Affix

 view release on metacpan or  search on metacpan

CODE_OF_CONDUCT.md  view on Meta::CPAN

or harmful.

Community leaders have the right and responsibility to remove, edit, or reject
comments, commits, code, wiki edits, issues, and other contributions that are
not aligned to this Code of Conduct, and will communicate reasons for moderation
decisions when appropriate.

## Scope

This Code of Conduct applies within all community spaces, and also applies when
an individual is officially representing the community in public spaces.
Examples of representing our community include using an official e-mail address,
posting via an official social media account, or acting as an appointed
representative at an online or offline event.

## Enforcement

Instances of abusive, harassing, or otherwise unacceptable behavior may be
reported to the community leaders responsible for enforcement at
https://github.com/sanko/Affix.pm/discussions.
All complaints will be reviewed and investigated promptly and fairly.

CODE_OF_CONDUCT.md  view on Meta::CPAN

Community leaders will follow these Community Impact Guidelines in determining
the consequences for any action they deem in violation of this Code of Conduct:

### 1. Correction

**Community Impact**: Use of inappropriate language or other behavior deemed
unprofessional or unwelcome in the community.

**Consequence**: A private, written warning from community leaders, providing
clarity around the nature of the violation and an explanation of why the
behavior was inappropriate. A public apology may be requested.

### 2. Warning

**Community Impact**: A violation through a single incident or series
of actions.

**Consequence**: A warning with consequences for continued behavior. No
interaction with the people involved, including unsolicited interaction with
those enforcing the Code of Conduct, for a specified period of time. This
includes avoiding interactions in community spaces as well as external channels
like social media. Violating these terms may lead to a temporary or
permanent ban.

### 3. Temporary Ban

**Community Impact**: A serious violation of community standards, including
sustained inappropriate behavior.

**Consequence**: A temporary ban from any sort of interaction or public
communication with the community for a specified period of time. No public or
private interaction with the people involved, including unsolicited interaction
with those enforcing the Code of Conduct, is allowed during this period.
Violating these terms may lead to a permanent ban.

### 4. Permanent Ban

**Community Impact**: Demonstrating a pattern of violation of community
standards, including sustained inappropriate behavior,  harassment of an
individual, or aggression toward or disparagement of classes of individuals.

**Consequence**: A permanent ban from any sort of public interaction within
the community.

## Attribution

This Code of Conduct is adapted from the [Contributor Covenant][homepage],
version 2.0, available at
https://www.contributor-covenant.org/version/2/0/code_of_conduct.html.

Community Impact Guidelines were inspired by [Mozilla's code of conduct
enforcement ladder](https://github.com/mozilla/diversity).

Changes.md  view on Meta::CPAN

  - Fixed `CLONE` to correctly copy user-defined types (typedefs, structs) to new threads. Previously, child threads started with an empty registry, causing lookup failures for types defined in the parent.
  - Thread safety: Fixed a crash when callbacks are invoked from foreign threads. Affix now correctly injects the Perl interpreter context into the TLS before executing the callback.
  - Added stack overflow protection to the FFI trigger. Argument marshalling buffers larger than 2KB are now allocated on the heap (arena) instead of the stack, preventing crashes on Windows and other platforms with limited stack sizes.
  - Type resolution: Fixed a logic bug where `Pointer[SV]` types were incorrectly treated as generic pointers if `typedef`'d. They are now correctly unwrapped into Perl CODE refs or blessed objects.
  - Process exit: Disabled explicit library unloading (`dlclose`/`FreeLibrary`) during global destruction. This prevents segmentation faults when background threads from loaded libraries try to execute code that has been unmapped from memory during s...
    I tried to just limit it to Go lang libs but it's just more trouble than it's worth until I resolve a few more things.
  - \[infix] Fixed stack corruption on macOS ARM64 (Apple Silicon). `long double` on this platform is 8 bytes (an alias for `double`), unlike standard AAPCS64 where it is 16 bytes. The JIT previously emitted 16-byte stores (`STR Qn`) for these types,...
  - \[infix] Fixed `long double` handling on macOS Intel (Darwin). Verified that Apple adheres to the System V ABI for this type: it requires 16-byte stack alignment and returns values on the x87 FPU stack (`ST(0)`).
  - \[infix] Fixed a generic System V ABI bug where 128-bit types (vectors, `__int128`) were not correctly aligned to 16 bytes on the stack relative to the return address, causing data corruption when mixed with odd numbers of 8-byte arguments.
  - \[infix] Enforced natural alignment for stack arguments in the AAPCS64 implementation. Previously, arguments were packed to 8-byte boundaries, which violated alignment requirements for 128-bit types.
  - \[infix] Fixed a critical deployment issue where the public `infix.h` header included an internal file (`common/compat_c23.h`). The header is now fully self-contained and defines `INFIX_NODISCARD` for attribute compatibility.
  - \[infix] Fixed 128-bit vector truncation on System V x64 (Linux/macOS). Reverse trampolines previously used 64-bit moves (`MOVSD`) for all SSE arguments, corrupting the upper half of vector arguments. They now correctly use `MOVUPS`.
  - \[infix] Fixed vector argument corruption on AArch64. The reverse trampoline generator now correctly identifies vector types and uses 128-bit stores (`STR Qn`) instead of falling back to 64-bit/32-bit stores or GPRs.
  - \[infix] Fixed floating-point corruption on Windows on ARM64. Reverse trampolines now force full 128-bit register saves for all floating-point arguments to ensure robust handling of volatile register states.
  - \[infix] Fixed a logic error in the System V reverse argument classifier where vectors were defaulting to `INTEGER` class, causing the trampoline to look in `RDI`/`RSI` instead of `XMM` registers.
  - \[infix] Fixed potential cache coherency issues on Windows x64. The library now unconditionally calls `FlushInstructionCache` after JIT compilation.
  - \[infix] Capped the maximum alignment in `infix_type_create_packed_struct` to 1MB to prevent integer wrap-around bugs in layout calculation.
  - \[infix] Fixed a buffer overread on macOS ARM64 where small signed integers were loaded using 32-bit `LDRSW`. Implemented `LDRSH` and `LDRSB`.
  - \[infix] Added native support for Apple's Hardened Runtime security policy.
    - The JIT engine now utilizes `MAP_JIT` when the `com.apple.security.cs.allow-jit` entitlement is detected.
    - Implemented thread-local permission toggling via `pthread_jit_write_protect_np` to maintain W^X compliance.

SECURITY.md  view on Meta::CPAN

## Supported Versions

| Version    | Supported          |
| ---------- | ------------------ |
| v1.0.x     | :white_check_mark: |
| v1.0.6     | :white_check_mark: |
| \<= v1.0.5 | :x:                |

# Reporting a Vulnerability

If you have any issue regarding security, please disclose the information responsibly by sending a report to https://github.com/sanko/Affix.pm/security/advisories/new and *not* at the public issue tracker or via email.

# Vulnerability Disclosure Policy

Maintaining the security of our open-source software is paramount. This policy outlines a responsible approach to addressing vulnerabilities, balancing transparency with the need to protect users.

- Security vulnerabilities identified in the project will be assigned a unique identifier and (if applicable) a Common Vulnerabilities and Exposures (CVE) identifier.

- The project's Maintainers will be responsible for addressing the vulnerability through a standard pull request, backporting the fix to immediate prior minor release branch, and including the fix in the next stable release.

- Release notes for the patched version will include the assigned identifier and, if applicable, the CVE identifier for the vulnerability.

- A grace period will be provided for Maintainers to update the vulerable minor version and remove vulerable releases from PAUSE (nothing can be done about backpan).

  This period will be one month for non-critical vulnerabilities and three months for critical vulnerabilities.

- After the grace period has elapsed, the vulnerability details will be made public.

infix/LICENSE-CC  view on Meta::CPAN

Attribution 4.0 International

=======================================================================

Creative Commons Corporation ("Creative Commons") is not a law firm and
does not provide legal services or legal advice. Distribution of
Creative Commons public licenses does not create a lawyer-client or
other relationship. Creative Commons makes its licenses and related
information available on an "as-is" basis. Creative Commons gives no
warranties regarding its licenses, any material licensed under their
terms and conditions, or any related information. Creative Commons
disclaims all liability for damages resulting from their use to the
fullest extent possible.

Using Creative Commons Public Licenses

Creative Commons public licenses provide a standard set of terms and
conditions that creators and other rights holders may use to share
original works of authorship and other material subject to copyright
and certain other rights specified in the public license below. The
following considerations are for informational purposes only, are not
exhaustive, and do not form part of our licenses.

     Considerations for licensors: Our public licenses are
     intended for use by those authorized to give the public
     permission to use material in ways otherwise restricted by
     copyright and certain other rights. Our licenses are
     irrevocable. Licensors should read and understand the terms
     and conditions of the license they choose before applying it.
     Licensors should also secure all rights necessary before
     applying our licenses so that the public can reuse the
     material as expected. Licensors should clearly mark any
     material not subject to the license. This includes other CC-
     licensed material, or material used under an exception or
     limitation to copyright. More considerations for licensors:
    wiki.creativecommons.org/Considerations_for_licensors

     Considerations for the public: By using one of our public
     licenses, a licensor grants the public permission to use the
     licensed material under specified terms and conditions. If
     the licensor's permission is not necessary for any reason--for
     example, because of any applicable exception or limitation to
     copyright--then that use is not regulated by the license. Our
     licenses grant only permissions under copyright and certain
     other rights that a licensor has authority to grant. Use of
     the licensed material may still be restricted for other
     reasons, including because others have copyright or other
     rights in the material. A licensor may make special requests,
     such as asking that all changes be marked or described.
     Although not required by our licenses, you are encouraged to
     respect those requests where reasonable. More considerations
     for the public:
    wiki.creativecommons.org/Considerations_for_licensees

=======================================================================

Creative Commons Attribution 4.0 International Public License

By exercising the Licensed Rights (defined below), You accept and agree
to be bound by the terms and conditions of this Creative Commons
Attribution 4.0 International Public License ("Public License"). To the
extent this Public License may be interpreted as a contract, You are

infix/LICENSE-CC  view on Meta::CPAN

     License.

  g. Licensed Rights means the rights granted to You subject to the
     terms and conditions of this Public License, which are limited to
     all Copyright and Similar Rights that apply to Your use of the
     Licensed Material and that the Licensor has authority to license.

  h. Licensor means the individual(s) or entity(ies) granting rights
     under this Public License.

  i. Share means to provide material to the public by any means or
     process that requires permission under the Licensed Rights, such
     as reproduction, public display, public performance, distribution,
     dissemination, communication, or importation, and to make material
     available to the public including in ways that members of the
     public may access the material from a place and at a time
     individually chosen by them.

  j. Sui Generis Database Rights means rights other than copyright
     resulting from Directive 96/9/EC of the European Parliament and of
     the Council of 11 March 1996 on the legal protection of databases,
     as amended and/or succeeded, as well as other essentially
     equivalent rights anywhere in the world.

  k. You means the individual or entity exercising the Licensed Rights
     under this Public License. Your has a corresponding meaning.

infix/LICENSE-CC  view on Meta::CPAN

       6. No endorsement. Nothing in this Public License constitutes or
          may be construed as permission to assert or imply that You
          are, or that Your use of the Licensed Material is, connected
          with, or sponsored, endorsed, or granted official status by,
          the Licensor or others designated to receive attribution as
          provided in Section 3(a)(1)(A)(i).

  b. Other rights.

       1. Moral rights, such as the right of integrity, are not
          licensed under this Public License, nor are publicity,
          privacy, and/or other similar personality rights; however, to
          the extent possible, the Licensor waives and/or agrees not to
          assert any such rights held by the Licensor to the limited
          extent necessary to allow You to exercise the Licensed
          Rights, but not otherwise.

       2. Patent and trademark rights are not licensed under this
          Public License.

       3. To the extent possible, the Licensor waives any right to

infix/LICENSE-CC  view on Meta::CPAN

     Licensor.

  d. Nothing in this Public License constitutes or may be interpreted
     as a limitation upon, or waiver of, any privileges and immunities
     that apply to the Licensor or You, including from the legal
     processes of any jurisdiction or authority.


=======================================================================

Creative Commons is not a party to its public
licenses. Notwithstanding, Creative Commons may elect to apply one of
its public licenses to material it publishes and in those instances
will be considered the “Licensor.” The text of the Creative Commons
public licenses is dedicated to the public domain under the CC0 Public
Domain Dedication. Except for the limited purpose of indicating that
material is shared under a Creative Commons public license or as
otherwise permitted by the Creative Commons policies published at
creativecommons.org/policies, Creative Commons does not authorize the
use of the trademark "Creative Commons" or any other trademark or logo
of Creative Commons without its prior written consent including,
without limitation, in connection with any unauthorized modifications
to any of its public licenses or any other arrangements,
understandings, or agreements concerning use of licensed material. For
the avoidance of doubt, this paragraph does not form part of the
public licenses.

Creative Commons may be contacted at creativecommons.org.

infix/include/infix/infix.h  view on Meta::CPAN

 *
 * SPDX-License-Identifier: (Artistic-2.0 OR MIT)
 *
 * The documentation blocks within this file are licensed under the
 * Creative Commons Attribution 4.0 International License (CC BY 4.0).
 *
 * SPDX-License-Identifier: CC-BY-4.0
 */
/**
 * @file infix.h
 * @brief The public interface for the infix FFI library.
 *
 * @mainpage infix FFI Library
 *
 * @section intro_sec Introduction
 *
 * `infix` is a powerful, modern, and lightweight C library for creating Foreign
 * Function Interface (FFI) trampolines at runtime. It allows you to dynamically
 * call C functions or create C callbacks from any language or environment, using
 * a simple, human-readable string-based syntax to describe function signatures.
 *

infix/src/common/compat_c23.h  view on Meta::CPAN

 * @param[in] x The name of the attribute to check (e.g., `nodiscard`).
 * @return `1` if the attribute is supported, `0` otherwise.
 */
#if defined(__has_c_attribute)
#define COMPAT_HAS_C_ATTRIBUTE(x) __has_c_attribute(x)
#else
#define COMPAT_HAS_C_ATTRIBUTE(x) 0
#endif
/**
 * @def c23_nodiscard
 * @brief Internal alias for the public INFIX_NODISCARD macro.
 */
#define c23_nodiscard INFIX_NODISCARD
/**
 * @def c23_deprecated
 * @brief A compatibility macro for the C23 `[[deprecated]]` attribute.
 *
 * @details This attribute is used to mark a function or type as obsolete. The
 * compiler will issue a warning if any code attempts to use a deprecated entity,
 * guiding users toward newer APIs and helping to manage API evolution.
 *

infix/src/common/compat_c23.h  view on Meta::CPAN

#else
#define c23_fallthrough
#endif
/**
 * @def c23_maybe_unused
 * @brief A compatibility macro for the C23 `[[maybe_unused]]` attribute.
 *
 * @details This attribute suppresses compiler warnings about unused variables,
 * parameters, or functions. It is useful for parameters that are only used in
 * certain build configurations (e.g., in an `#ifdef DEBUG` block) or for
 * functions that are part of a public API but not used internally.
 *
 * This macro expands to:
 * - `[[maybe_unused]]` on compilers that support the C23 standard syntax.
 * - `__attribute__((unused))` on GCC and Clang.
 * - Nothing on other compilers.
 */
#if COMPAT_HAS_C_ATTRIBUTE(maybe_unused)
#define c23_maybe_unused [[maybe_unused]]
#elif defined(INFIX_COMPILER_GCC) || defined(INFIX_COMPILER_CLANG)
#define c23_maybe_unused __attribute__((unused))

infix/src/common/infix_internals.h  view on Meta::CPAN

 * Creative Commons Attribution 4.0 International License (CC BY 4.0).
 *
 * SPDX-License-Identifier: CC-BY-4.0
 */
/**
 * @file infix_internals.h
 * @brief Internal data structures, function prototypes, and constants.
 * @ingroup internal_common
 *
 * @details This is the primary internal header for the `infix` library. It defines the
 * complete layout of all opaque public structs (like `infix_forward_t`) and
 * declares internal-only functions (`_infix_*`) that are shared between modules.
 *
 * Its most important role is to define the core ABI abstraction layer through v-tables
 * (`infix_forward_abi_spec`, `infix_reverse_abi_spec`). These structures form the
 * contract between the platform-agnostic JIT engine (`trampoline.c`) and the
 * platform-specific ABI implementations (`arch/...`), making them key to the
 * library's portability and architectural design.
 *
 * This header also brings together all other internal type definitions, creating a
 * single source of truth for the library's internal data model.

infix/src/common/infix_internals.h  view on Meta::CPAN

 * @param code The `infix` error code that corresponds to the failure.
 * @param system_code The OS-specific error code (e.g., from `errno` or `GetLastError`).
 * @param msg An optional custom message from the OS (e.g., from `dlerror`).
 */
INFIX_INTERNAL void _infix_set_system_error(infix_error_category_t category,
                                            infix_error_code_t code,
                                            long system_code,
                                            const char * msg);
/**
 * @brief Clears the thread-local error state.
 * @details Located in `src/core/error.c`. This is called at the beginning of every public
 * API function to ensure that a prior error from an unrelated call is not accidentally returned.
 */
INFIX_INTERNAL void _infix_clear_error(void);
INFIX_INTERNAL void skip_whitespace(parser_state * state);
INFIX_INTERNAL void _infix_set_parser_error(parser_state * state, infix_error_code_t code);
INFIX_INTERNAL infix_type * parse_type(parser_state * state);
INFIX_INTERNAL infix_type * parse_primitive(parser_state * state);

/**
 * @brief Recalculates the layout of a fully resolved type graph.

infix/src/core/error.c  view on Meta::CPAN

 *
 * @details This module provides the infrastructure for robust and thread-safe error
 * handling within the `infix` library.
 *
 * The core principle is that all detailed error information is stored in
 * **thread-local storage (TLS)**. This means that an error occurring in one thread
 * will never interfere with or be accidentally reported by an operation in another
 * thread.
 *
 * The workflow is as follows:
 * 1.  Every public API function calls `_infix_clear_error()` upon entry to reset the
 *     error state for the current thread.
 * 2.  If an internal function encounters an error, it calls `_infix_set_error()` or
 *     `_infix_set_system_error()` to record detailed diagnostic information, including
 *     an error code, category, and a descriptive message.
 * 3.  For parser errors, `_infix_set_error()` generates a rich, multi-line diagnostic
 *     message with a code snippet and a caret pointing to the error location, similar
 *     to a compiler error.
 * 4.  The user can call the public `infix_get_last_error()` function at any time to
 *     retrieve a copy of the last error that occurred on their thread.
 */
#include "common/infix_internals.h"
#include <infix/infix.h>
#include <stdarg.h>
#include <stdio.h>  // For snprintf
#include <string.h>

// Use a portable mechanism for thread-local storage (TLS).
// The order of checks is critical for cross-platform compatibility.

infix/src/core/error.c  view on Meta::CPAN

    else {
        const char * default_msg = _get_error_message_for_code(code);
        _INFIX_SAFE_STRNCPY(g_infix_last_error.message, default_msg, sizeof(g_infix_last_error.message) - 1);
    }
}

/**
 * @internal
 * @brief Resets the error state for the current thread to "no error".
 *
 * This should be called at the beginning of every public API function to ensure
 * that a prior error from an unrelated call on the same thread is not accidentally
 * returned to the user.
 */
void _infix_clear_error(void) {
    g_infix_last_error.category = INFIX_CATEGORY_NONE;
    g_infix_last_error.code = INFIX_CODE_SUCCESS;
    g_infix_last_error.position = 0;
    g_infix_last_error.system_error_code = 0;
    g_infix_last_error.message[0] = '\0';
    g_infix_last_signature_context = nullptr;

infix/src/core/signature.c  view on Meta::CPAN

 *
 * 1.  **Parsing:** It contains a hand-written recursive descent parser that transforms a
 *     human-readable signature string (e.g., `"({int, *char}) -> void"`) into an
 *     unresolved `infix_type` object graph. This is the **"Parse"** stage of the core
 *     data pipeline. The internal entry point for the "Parse" stage is `_infix_parse_type_internal`.
 *
 * 2.  **Printing:** It provides functions to serialize a fully resolved `infix_type`
 *     graph back into a canonical signature string. This is crucial for introspection,
 *     debugging, and verifying the library's understanding of a type.
 *
 * The public functions `infix_type_from_signature` and `infix_signature_parse`
 * are high-level orchestrators. They manage the entire **"Parse -> Copy -> Resolve -> Layout"**
 * pipeline, providing the user with a fully validated, self-contained, and ready-to-use
 * type object that is safe to use for the lifetime of its returned arena.
 */
#include "common/infix_internals.h"
#include <ctype.h>
#include <stdarg.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>

infix/src/core/signature.c  view on Meta::CPAN

}
// High-Level API Implementation
/**
 * @internal
 * @brief The internal entry point for the signature parser (the "Parse" stage).
 *
 * This function takes a signature string and produces a raw, unresolved type
 * graph in a new, temporary arena. It is the core parsing logic, separated from the
 * higher-level functions that manage the full data pipeline. It is careful not to
 * modify the global error context string (`g_infix_last_signature_context`), which
 * is the responsibility of its public API callers.
 *
 * @param[out] out_type On success, receives the parsed type graph.
 * @param[out] out_arena On success, receives the temporary arena holding the graph. The caller is responsible for
 * destroying it.
 * @param[in] signature The signature string to parse.
 * @return `INFIX_SUCCESS` on success.
 */
c23_nodiscard infix_status _infix_parse_type_internal(infix_type ** out_type,
                                                      infix_arena_t ** out_arena,
                                                      const char * signature) {
    if (!out_type || !out_arena) {
        _infix_set_error(INFIX_CATEGORY_GENERAL, INFIX_CODE_NULL_POINTER, 0);
        return INFIX_ERROR_INVALID_ARGUMENT;
    }
    if (!signature || *signature == '\0') {
        _infix_set_error(INFIX_CATEGORY_PARSER, INFIX_CODE_EMPTY_SIGNATURE, 0);
        return INFIX_ERROR_INVALID_ARGUMENT;
    }
    // The top-level public API is responsible for setting g_infix_last_signature_context.
    *out_arena = infix_arena_create(4096);
    if (!*out_arena) {
        _infix_set_error(INFIX_CATEGORY_ALLOCATION, INFIX_CODE_OUT_OF_MEMORY, 0);
        return INFIX_ERROR_ALLOCATION_FAILED;
    }
    parser_state state = {.p = signature, .start = signature, .arena = *out_arena, .depth = 0};
    infix_type * type = parse_type(&state);
    if (type) {
        skip_whitespace(&state);
        // After successfully parsing a type, ensure there is no trailing junk.

infix/src/core/types.c  view on Meta::CPAN

 *
 * SPDX-License-Identifier: (Artistic-2.0 OR MIT)
 *
 * The documentation blocks within this file are licensed under the
 * Creative Commons Attribution 4.0 International License (CC BY 4.0).
 *
 * SPDX-License-Identifier: CC-BY-4.0
 */
/**
 * @file types.c
 * @brief Implements the public API for creating and managing type descriptions.
 * @ingroup internal_core
 *
 * @details This module serves two primary functions:
 * 1.  It provides the public functions for programmatically constructing `infix_type`
 *     objects (the "Manual API"). These functions are the building blocks for
 *     users who need to create type information dynamically without parsing strings.
 * 2.  It contains the crucial internal logic for two core stages of the data pipeline:
 *     - **Copying (`_copy_type_graph_to_arena`):** Deep-copies a type graph to a
 *       new memory arena, which is fundamental to creating self-contained trampoline
 *       objects and ensuring memory safety.
 *     - **Layout (`_infix_type_recalculate_layout`):** Traverses a fully resolved
 *       type graph to compute the final memory layout (size, alignment, and offsets)
 *       of all structures and unions.
 *

infix/src/jit/trampoline.c  view on Meta::CPAN

        infix_forward_destroy(handle);
    // The temporary arena is always destroyed.
    infix_arena_destroy(temp_arena);
    return status;
}
/**
 * @internal
 * @brief The core implementation for creating a direct marshalling forward trampoline.
 *
 * This function orchestrates the JIT compilation pipeline for the direct marshalling
 * feature. It is the internal counterpart to the public `infix_forward_create_direct`
 * function and is called after the signature string has been parsed into a type graph.
 *
 * The pipeline is as follows:
 * 1.  Selects the appropriate `infix_direct_forward_abi_spec` v-table for the target platform.
 * 2.  Invokes `prepare_direct_forward_call_frame` to analyze the signature and handlers,
 *     producing a complete layout blueprint.
 * 3.  Calls the `generate_*` functions from the v-table in sequence. This emits machine code
 *     that includes direct calls to the user-provided marshaller and write-back functions.
 * 4.  Finalizes the `infix_forward_t` handle, marking it as a `is_direct_trampoline`.
 * 5.  Allocates executable memory, copies the generated code, and makes it executable.

lib/Affix/Build.pm  view on Meta::CPAN

                # ocamlopt -shared -o lib.so file.ml
                $self->_run( $ml, '-shared', "$file", '-o', "$out" );
                return $out;
            }
            my $obj = $build_dir->child( $self->_base($file) . $Config{_o} );
            $self->_run( $ml, '-output-obj', "$file", '-o', "$obj" );
            return { file => $obj };
        }

        #~ https://wiki.liberty-eiffel.org/index.php/Compile
        #~ https://svn.eiffel.com/eiffelstudio-public/branches/Eiffel_54/Delivery/docs/papers/dll.html
        method _build_eiffel ( $file, $out, $mode ) {
            my $se = $self->_can_run('se') // croak "SmartEiffel not found";

            # Transpile to C
            my $c_file = $build_dir->child( $self->_base($file) . '.c' );
            $self->_run( $se, 'c', '-o', "$c_file", "$file" );

            # Reuse C builder
            return $self->_build_c( $c_file, $out, $mode );
        }

t/017_affix_build.t  view on Meta::CPAN

    #endif
    extern "C" {
        EXPORT int add_cpp(int a, int b) {
            return a + b;
        }
    }

run_test( 'csharp', 'C#', <<~'', 'add_cs', 'dotnet', \&check_dotnet );
    using System.Runtime.InteropServices;
    namespace T {
        public class C {
            [UnmanagedCallersOnly(EntryPoint="add_cs")]
            public static int Add(int a, int b) => a + b;
        }
    }

run_test( 'rust', 'Rust', <<~'', 'add_rs', 'rustc' );
    #[no_mangle]
    pub extern "C" fn add_rs(a: i32, b: i32) -> i32 {
        a + b
    }

run_test( 'go', 'Go', <<~'', 'add_go', 'go' );

t/017_affix_build.t  view on Meta::CPAN

    exports add_pas;
    begin end.

run_test( 'cr', 'Crystal', <<~'', 'add_cr', 'crystal' );
    fun add_cr(a : Int32, b : Int32) : Int32
      a + b
    end

run_test( 'swift', 'Swift', <<~'', 'add_swift', 'swiftc' );
    @_cdecl("add_swift")
    public func add_swift(a: Int32, b: Int32) -> Int32 {
        return a + b
    }

run_test( 'assembly', 'Assembly', $Config{archname} =~ /arm64|aarch64/ ? <<~'' : $^O eq 'MSWin32' ? <<~'': <<~'', 'add_asm', 'nasm' );
        ; ARM64: add w0, w0, w1
        .global add_asm
        .text
        .align 2
        add_asm:
            add w0, w0, w1

t/050_affix_build.t  view on Meta::CPAN

    #endif
    extern "C" {
        EXPORT int add_cpp(int a, int b) {
            return a + b;
        }
    }

run_test( 'csharp', 'C#', <<~'', 'add_cs', 'dotnet', \&check_dotnet );
    using System.Runtime.InteropServices;
    namespace T {
        public class C {
            [UnmanagedCallersOnly(EntryPoint="add_cs")]
            public static int Add(int a, int b) => a + b;
        }
    }

run_test( 'rust', 'Rust', <<~'', 'add_rs', 'rustc' );
    #[no_mangle]
    pub extern "C" fn add_rs(a: i32, b: i32) -> i32 {
        a + b
    }

run_test( 'go', 'Go', <<~'', 'add_go', 'go' );

t/050_affix_build.t  view on Meta::CPAN

    exports add_pas;
    begin end.

run_test( 'cr', 'Crystal', <<~'', 'add_cr', 'crystal' );
    fun add_cr(a : Int32, b : Int32) : Int32
      a + b
    end

run_test( 'swift', 'Swift', <<~'', 'add_swift', 'swiftc' );
    @_cdecl("add_swift")
    public func add_swift(a: Int32, b: Int32) -> Int32 {
        return a + b
    }

run_test( 'assembly', 'Assembly', $Config{archname} =~ /arm64|aarch64/ ? <<~'' : $^O eq 'MSWin32' ? <<~'': <<~'', 'add_asm', 'nasm' );
        ; ARM64: add w0, w0, w1
        .global add_asm
        .text
        .align 2
        add_asm:
            add w0, w0, w1



( run in 2.712 seconds using v1.01-cache-2.11-cpan-39bf76dae61 )