<commit_before>/*
Copyright (C) 2010-2011, Parrot Foundation.

=head1 NAME

src/embed/api.c - The Parrot embedding interface

=head1 DESCRIPTION

This file implements functions of the Parrot embedding interface.

=head2 Functions

=over 4

=cut

*/

#include "parrot/parrot.h"
#include "parrot/runcore_api.h"
#include "parrot/embed.h"
#include "parrot/api.h"
#include "embed_private.h"

/* HEADERIZER HFILE: include/parrot/api.h */


/*

=item C<Parrot_Int Parrot_api_get_result(Parrot_PMC interp_pmc, Parrot_Int
*is_error, Parrot_PMC * exception, Parrot_Int *exit_code, Parrot_String *
errmsg)>

Gets the results of the last API function call and stores the results in
C<is_error>, C<exception>, C<exit_code> and C<errmsg>. This function returns
a true value if this call is successful and false value otherwise. The stored
information is as follow:

C<is_error> a true value if an unhandled exception was thrown or the program
terminated with an error condition and a false value otherwise.

C<exception> the last exception thrown.

C<exit_code> the exit code of the running program.

C<errmsg> contains an string with the last error message.

=cut

*/

PARROT_API
Parrot_Int
Parrot_api_get_result(Parrot_PMC interp_pmc, ARGOUT(Parrot_Int *is_error),
        ARGOUT(Parrot_PMC * exception), ARGOUT(Parrot_Int *exit_code),
        ARGOUT(Parrot_String * errmsg))
{
    ASSERT_ARGS(Parrot_api_get_result)
    EMBED_API_CALLIN(interp_pmc, interp)
    *exit_code = interp->exit_code;
    *exception = interp->final_exception;
    if (PMC_IS_NULL(*exception)) {
        *is_error = 0;
        *errmsg = STRINGNULL;
    }
    else {
        STRING * const severity_str = Parrot_str_new(interp, "severity", 0);
        INTVAL severity = VTABLE_get_integer_keyed_str(interp, *exception, severity_str);
        *is_error = (severity != EXCEPT_exit);
        *errmsg = VTABLE_get_string(interp, *exception);
    }
    interp->final_exception = PMCNULL;
    interp->exit_code = 0;
    EMBED_API_CALLOUT(interp_pmc, interp)
}

/*

=item C<Parrot_Int Parrot_api_get_exception_backtrace(Parrot_PMC interp_pmc,
Parrot_PMC exception, Parrot_String * bt)>

Gets the backtrace of the interpreter's call chain for the given exception
C<expcetion> and stores the results in string C<bt>. This function returns a
true value if this call is successful and false value otherwise.

=cut

*/

PARROT_API
Parrot_Int
Parrot_api_get_exception_backtrace(Parrot_PMC interp_pmc,
        Parrot_PMC exception, ARGOUT(Parrot_String * bt))
{
    ASSERT_ARGS(Parrot_api_get_exception_backtrace)
    EMBED_API_CALLIN(interp_pmc, interp)
    if (PMC_IS_NULL(exception))
        *bt = STRINGNULL;
    else
        *bt = Parrot_ex_build_complete_backtrace_string(interp, exception);
    EMBED_API_CALLOUT(interp_pmc, interp)
}


/*

=item C<Parrot_Int Parrot_api_make_interpreter(Parrot_PMC parent, Parrot_Int
flags, Parrot_Init_Args *args, Parrot_PMC *interp)>

Creates a new interpreter and stores it in C<interp>. It takes three optional
parameters the new interpreter's C<flags>, the initialization paremeters C<args>
and the C<parent> interpreter. This function returns a true value if this call
is successful and false value otherwise.

=cut

*/

PARROT_API
Parrot_Int
Parrot_api_make_interpreter(Parrot_PMC parent, Parrot_Int flags,
        ARGIN_NULLOK(Parrot_Init_Args *args), ARGOUT(Parrot_PMC *interp))
{
    ASSERT_ARGS(Parrot_api_make_interpreter)
    int alt_stacktop;
    Parrot_Interp interp_raw;
    Parrot_GC_Init_Args gc_args;
    const Parrot_Interp parent_raw = PMC_IS_NULL(parent) ? NULL : GET_RAW_INTERP(parent);
    interp_raw = allocate_interpreter(parent_raw, flags);
    if (args) {
        gc_args.stacktop          = args->stacktop
                                  ? args->stacktop : &alt_stacktop;
        gc_args.system            = args->gc_system;
        gc_args.dynamic_threshold = args->gc_dynamic_threshold;
        gc_args.min_threshold     = args->gc_min_threshold;

        if (args->hash_seed)
            interp_raw->hash_seed = args->hash_seed;
    }
    else {
        memset(&gc_args, 0, sizeof (Parrot_GC_Init_Args));
        gc_args.stacktop = &alt_stacktop;
    }
    initialize_interpreter(interp_raw, &gc_args);
    *interp = VTABLE_get_pmc_keyed_int(
            interp_raw, interp_raw->iglobals, (Parrot_Int)IGLOBALS_INTERPRETER);
    return !PMC_IS_NULL(*interp);
}

/*

=item C<Parrot_Int Parrot_api_set_runcore(Parrot_PMC interp_pmc, const char *
corename, Parrot_UInt trace)>

Sets the C<interp_pmc>'s bytecode running core, the core is specified by the
C<corename>. This function returns a true value if this call is successful and
false value otherwise.

=cut

*/

PARROT_API
Parrot_Int
Parrot_api_set_runcore(Parrot_PMC interp_pmc, ARGIN(const char * corename),
        Parrot_UInt trace)
{
    ASSERT_ARGS(Parrot_api_set_runcore)
    EMBED_API_CALLIN(interp_pmc, interp)
    if (trace) {
        Interp_trace_SET(interp, PARROT_TRACE_OPS_FLAG);
        Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "slow"));
    }
    else {
        if (!strcmp(corename, "slow") || !strcmp(corename, "bounds"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "slow"));
        else if (!strcmp(corename, "fast") ||
            !strcmp(corename, "jit") || !strcmp(corename, "function"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "fast"));
        else if (!strcmp(corename, "exec"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "exec"));
        else if (!strcmp(corename, "trace")) {
            Interp_trace_SET(interp, PARROT_TRACE_OPS_FLAG);
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "slow"));
        }
        else if (!strcmp(corename, "profiling"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "profiling"));
        else if (!strcmp(corename, "gcdebug"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "gcdebug"));
        else
            Parrot_ex_throw_from_c_args(interp, NULL, 1, "Invalid runcore type %s", corename);
    }
    EMBED_API_CALLOUT(interp_pmc, interp)
}

/*

=item C<Parrot_Int Parrot_api_debug_flag(Parrot_PMC interp_pmc, Parrot_Int
flags, Parrot_Int set)>

Sets/Unsets the C<interp_pmc>'s debug flags. If C<set> is in a true value debug
flags are set otherwise debug flags are cleared. This function returns a true
value if this call is successful and false value otherwise.

=cut

*/

PARROT_API<commit_msg>Use STREQ() for string comparisons, instead of incorrectly using strcmp as a boolean<commit_after>/*
Copyright (C) 2010-2011, Parrot Foundation.

=head1 NAME

src/embed/api.c - The Parrot embedding interface

=head1 DESCRIPTION

This file implements functions of the Parrot embedding interface.

=head2 Functions

=over 4

=cut

*/

#include "parrot/parrot.h"
#include "parrot/runcore_api.h"
#include "parrot/embed.h"
#include "parrot/api.h"
#include "embed_private.h"

/* HEADERIZER HFILE: include/parrot/api.h */


/*

=item C<Parrot_Int Parrot_api_get_result(Parrot_PMC interp_pmc, Parrot_Int
*is_error, Parrot_PMC * exception, Parrot_Int *exit_code, Parrot_String *
errmsg)>

Gets the results of the last API function call and stores the results in
C<is_error>, C<exception>, C<exit_code> and C<errmsg>. This function returns
a true value if this call is successful and false value otherwise. The stored
information is as follow:

C<is_error> a true value if an unhandled exception was thrown or the program
terminated with an error condition and a false value otherwise.

C<exception> the last exception thrown.

C<exit_code> the exit code of the running program.

C<errmsg> contains an string with the last error message.

=cut

*/

PARROT_API
Parrot_Int
Parrot_api_get_result(Parrot_PMC interp_pmc, ARGOUT(Parrot_Int *is_error),
        ARGOUT(Parrot_PMC * exception), ARGOUT(Parrot_Int *exit_code),
        ARGOUT(Parrot_String * errmsg))
{
    ASSERT_ARGS(Parrot_api_get_result)
    EMBED_API_CALLIN(interp_pmc, interp)
    *exit_code = interp->exit_code;
    *exception = interp->final_exception;
    if (PMC_IS_NULL(*exception)) {
        *is_error = 0;
        *errmsg = STRINGNULL;
    }
    else {
        STRING * const severity_str = Parrot_str_new(interp, "severity", 0);
        INTVAL severity = VTABLE_get_integer_keyed_str(interp, *exception, severity_str);
        *is_error = (severity != EXCEPT_exit);
        *errmsg = VTABLE_get_string(interp, *exception);
    }
    interp->final_exception = PMCNULL;
    interp->exit_code = 0;
    EMBED_API_CALLOUT(interp_pmc, interp)
}

/*

=item C<Parrot_Int Parrot_api_get_exception_backtrace(Parrot_PMC interp_pmc,
Parrot_PMC exception, Parrot_String * bt)>

Gets the backtrace of the interpreter's call chain for the given exception
C<expcetion> and stores the results in string C<bt>. This function returns a
true value if this call is successful and false value otherwise.

=cut

*/

PARROT_API
Parrot_Int
Parrot_api_get_exception_backtrace(Parrot_PMC interp_pmc,
        Parrot_PMC exception, ARGOUT(Parrot_String * bt))
{
    ASSERT_ARGS(Parrot_api_get_exception_backtrace)
    EMBED_API_CALLIN(interp_pmc, interp)
    if (PMC_IS_NULL(exception))
        *bt = STRINGNULL;
    else
        *bt = Parrot_ex_build_complete_backtrace_string(interp, exception);
    EMBED_API_CALLOUT(interp_pmc, interp)
}


/*

=item C<Parrot_Int Parrot_api_make_interpreter(Parrot_PMC parent, Parrot_Int
flags, Parrot_Init_Args *args, Parrot_PMC *interp)>

Creates a new interpreter and stores it in C<interp>. It takes three optional
parameters the new interpreter's C<flags>, the initialization paremeters C<args>
and the C<parent> interpreter. This function returns a true value if this call
is successful and false value otherwise.

=cut

*/

PARROT_API
Parrot_Int
Parrot_api_make_interpreter(Parrot_PMC parent, Parrot_Int flags,
        ARGIN_NULLOK(Parrot_Init_Args *args), ARGOUT(Parrot_PMC *interp))
{
    ASSERT_ARGS(Parrot_api_make_interpreter)
    int alt_stacktop;
    Parrot_Interp interp_raw;
    Parrot_GC_Init_Args gc_args;
    const Parrot_Interp parent_raw = PMC_IS_NULL(parent) ? NULL : GET_RAW_INTERP(parent);
    interp_raw = allocate_interpreter(parent_raw, flags);
    if (args) {
        gc_args.stacktop          = args->stacktop
                                  ? args->stacktop : &alt_stacktop;
        gc_args.system            = args->gc_system;
        gc_args.dynamic_threshold = args->gc_dynamic_threshold;
        gc_args.min_threshold     = args->gc_min_threshold;

        if (args->hash_seed)
            interp_raw->hash_seed = args->hash_seed;
    }
    else {
        memset(&gc_args, 0, sizeof (Parrot_GC_Init_Args));
        gc_args.stacktop = &alt_stacktop;
    }
    initialize_interpreter(interp_raw, &gc_args);
    *interp = VTABLE_get_pmc_keyed_int(
            interp_raw, interp_raw->iglobals, (Parrot_Int)IGLOBALS_INTERPRETER);
    return !PMC_IS_NULL(*interp);
}

/*

=item C<Parrot_Int Parrot_api_set_runcore(Parrot_PMC interp_pmc, const char *
corename, Parrot_UInt trace)>

Sets the C<interp_pmc>'s bytecode running core, the core is specified by the
C<corename>. This function returns a true value if this call is successful and
false value otherwise.

=cut

*/

PARROT_API
Parrot_Int
Parrot_api_set_runcore(Parrot_PMC interp_pmc, ARGIN(const char * corename),
        Parrot_UInt trace)
{
    ASSERT_ARGS(Parrot_api_set_runcore)
    EMBED_API_CALLIN(interp_pmc, interp)
    if (trace) {
        Interp_trace_SET(interp, PARROT_TRACE_OPS_FLAG);
        Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "slow"));
    }
    else {
        if (STREQ(corename, "slow") || STREQ(corename, "bounds"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "slow"));
        else if (STREQ(corename, "fast") || STREQ(corename, "jit") || STREQ(corename, "function"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "fast"));
        else if (STREQ(corename, "exec"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "exec"));
        else if (STREQ(corename, "trace")) {
            Interp_trace_SET(interp, PARROT_TRACE_OPS_FLAG);
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "slow"));
        }
        else if (STREQ(corename, "profiling"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "profiling"));
        else if (STREQ(corename, "gcdebug"))
            Parrot_runcore_switch(interp, Parrot_str_new_constant(interp, "gcdebug"));
        else
            Parrot_ex_throw_from_c_args(interp, NULL, 1, "Invalid runcore type %s", corename);
    }
    EMBED_API_CALLOUT(interp_pmc, interp)
}

/*

=item C<Parrot_Int Parrot_api_debug_flag(Parrot_PMC interp_pmc, Parrot_Int
flags, Parrot_Int set)>

Sets/Unsets the C<interp_pmc>'s debug flags. If C<set> is in a true value debug
flags are set otherwise debug flags are cleared. This function returns a true
value if this call is successful and false value otherwise.

=cut

*/

PARROT_API
{'fraction_non_alphanumeric': 0.08966831871902402, 'fraction_numerical': 0.0025924513915364087, 'mean_word_length': 4.08175125920186, 'pattern_counts': {'":': 0, '<': 49, '<?xml version=': 0, '>': 75, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 2, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6910845', 'n_tokens_mistral': 4651, 'n_tokens_neox': 4563, 'n_words': 1067}