<commit_before>#pragma once

#include "../../ast/func.hpp"
#include "../../ast/args.hpp"

namespace namu {

    template <typename Ret, typename T, template <typename, nbool> class Marshaling, typename... Args>
    class tcppBridgeFuncBase : public func {
        NAMU(ADT(tcppBridgeFuncBase, func))
    protected:
        typedef Ret (T::*fptrType)(Args...);

    public:
        tcppBridgeFuncBase(fptrType fptr): super(), _fptr(fptr) {}

        static_assert(allTrues<(sizeof(Marshaling<Args, tifSub<Args, node>::is>::canMarshal() ) ==
                sizeof(metaIf::yes))...>::value,
                "can't marshal one of this func's parameter ntypes.");

    public:
        using super::run;
        str run(const args& a) override {
            args tray;
            args& evaluated = _evalArgs(a, tray);
            if(nul(evaluated)) return NAMU_E("evaluated == null"), str();

            return _runNative(evaluated);
        }

        const node& getRet() const override {
            typedef Marshaling<Ret, tifSub<Ret, node>::is> marshaling;
            static typename marshaling::mgdType* inner = nullptr;
            if(nul(inner))
                inner = &marshaling::onGetRet();

            return *inner;
        }

        const params& getParams() const override;

        me* deepClone() const override {
            me* ret = (me*) clone();
            if(_params)
                ret->_params.bind(_params->deepClone());

            return ret;
        }

    protected:
        virtual str _runNative(args& args) = 0;

    private:
        args& _evalArgs(const args& a, args& tray) {
            const params& ps = getParams();
            if(a.len() != ps.len())
                return NAMU_E("length of a(%d) and typs(%d) doesn't match.", a.len(), ps.len()),
                       nulOf<args>();

            int n = 0;
            for(const node& e: a) {
                str ased = e.as(ps[n++].getOrigin());
                if(!ased) return nulOf<args>();

                tray.add(*ased);
            }
            tray.setMe(a.getMe());
            return tray;
        }

    protected:
        fptrType _fptr;
        mutable tstr<params> _params;
    };

    template <typename Ret, typename T, template <typename, nbool> class Marshaling,
             typename... Args><commit_msg>core: fix: return type of generic func doesn't change<commit_after>#pragma once

#include "../../ast/func.hpp"
#include "../../ast/args.hpp"

namespace namu {

    template <typename Ret, typename T, template <typename, nbool> class Marshaling, typename... Args>
    class tcppBridgeFuncBase : public func {
        NAMU(ADT(tcppBridgeFuncBase, func))
    protected:
        typedef Ret (T::*fptrType)(Args...);

    public:
        tcppBridgeFuncBase(fptrType fptr): super(), _fptr(fptr) {}

        static_assert(allTrues<(sizeof(Marshaling<Args, tifSub<Args, node>::is>::canMarshal() ) ==
                sizeof(metaIf::yes))...>::value,
                "can't marshal one of this func's parameter ntypes.");

    public:
        using super::run;
        str run(const args& a) override {
            args tray;
            args& evaluated = _evalArgs(a, tray);
            if(nul(evaluated)) return NAMU_E("evaluated == null"), str();

            return _runNative(evaluated);
        }

        const node& getRet() const override {
            if(!_ret)
                _ret.bind(Marshaling<Ret, tifSub<Ret, node>::is>::onGetRet());

            return *_ret;
        }

        nbool setRet(const node& newRet) override {
            return _ret.bind(newRet);
        }

        const params& getParams() const override;

        me* deepClone() const override {
            me* ret = (me*) clone();
            if(_params)
                ret->_params.bind(_params->deepClone());

            return ret;
        }

    protected:
        virtual str _runNative(args& args) = 0;

    private:
        args& _evalArgs(const args& a, args& tray) {
            const params& ps = getParams();
            if(a.len() != ps.len())
                return NAMU_E("length of a(%d) and typs(%d) doesn't match.", a.len(), ps.len()),
                       nulOf<args>();

            int n = 0;
            for(const node& e: a) {
                str ased = e.as(ps[n++].getOrigin());
                if(!ased) return nulOf<args>();

                tray.add(*ased);
            }
            tray.setMe(a.getMe());
            return tray;
        }

    protected:
        fptrType _fptr;
        mutable tstr<params> _params;
        mutable str _ret;
    };

    template <typename Ret, typename T, template <typename, nbool> class Marshaling,
             typename... Args>
{'fraction_non_alphanumeric': 0.13589961718417695, 'fraction_numerical': 0.0008507018290089324, 'mean_word_length': 1.85203153426319, 'pattern_counts': {'":': 0, '<': 27, '<?xml version=': 0, '>': 31, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '7305411', 'n_tokens_mistral': 1429, 'n_tokens_neox': 1357, 'n_words': 348}