FnCallResult FnCallEvaluate(EvalContext *ctx, FnCall *fp, const Promise *caller) { Rlist *expargs; const FnCallType *fp_type = FnCallTypeGet(fp->name); if (fp_type) { if (DEBUG) { printf("EVALUATE FN CALL %s\n", fp->name); FnCallShow(stdout, fp); printf("\n"); } } else { if (caller) { CfOut(OUTPUT_LEVEL_ERROR, "", "No such FnCall \"%s()\" in promise @ %s near line %zd\n", fp->name, PromiseGetBundle(caller)->source_path, caller->offset.line); } else { CfOut(OUTPUT_LEVEL_ERROR, "", "No such FnCall \"%s()\" - context info unavailable\n", fp->name); } return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } /* If the container classes seem not to be defined at this stage, then don't try to expand the function */ if ((caller != NULL) && !IsDefinedClass(ctx, caller->classes, PromiseGetNamespace(caller))) { return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } expargs = NewExpArgs(ctx, fp, caller); if (UnresolvedArgs(expargs)) { DeleteExpArgs(expargs); return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } fp->caller = caller; FnCallResult result = CallFunction(ctx, fp_type, fp, expargs); if (result.status == FNCALL_FAILURE) { /* We do not assign variables to failed function calls */ DeleteExpArgs(expargs); return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } DeleteExpArgs(expargs); return result; }
FnCallResult EvaluateFunctionCall(FnCall *fp, Promise *pp) { Rlist *expargs; const FnCallType *this = FindFunction(fp->name); if (this) { if (DEBUG) { printf("EVALUATE FN CALL %s\n", fp->name); ShowFnCall(stdout, fp); printf("\n"); } } else { if (pp) { CfOut(cf_error, "", "No such FnCall \"%s()\" in promise @ %s near line %zd\n", fp->name, pp->audit->filename, pp->offset.line); } else { CfOut(cf_error, "", "No such FnCall \"%s()\" - context info unavailable\n", fp->name); } return (FnCallResult) { FNCALL_FAILURE, { CopyFnCall(fp), CF_FNCALL } }; } /* If the container classes seem not to be defined at this stage, then don't try to expand the function */ if ((pp != NULL) && !IsDefinedClass(pp->classes)) { return (FnCallResult) { FNCALL_FAILURE, { CopyFnCall(fp), CF_FNCALL } }; } expargs = NewExpArgs(fp, pp); if (UnresolvedArgs(expargs)) { DeleteExpArgs(expargs); return (FnCallResult) { FNCALL_FAILURE, { CopyFnCall(fp), CF_FNCALL } }; } FnCallResult result = CallFunction(this, fp, expargs); if (result.status == FNCALL_FAILURE) { /* We do not assign variables to failed function calls */ DeleteExpArgs(expargs); return (FnCallResult) { FNCALL_FAILURE, { CopyFnCall(fp), CF_FNCALL } }; } DeleteExpArgs(expargs); return result; }
FnCallResult FnCallEvaluate(EvalContext *ctx, FnCall *fp, const Promise *caller) { fp->caller = caller; if (!(ctx->eval_options & EVAL_OPTION_EVAL_FUNCTIONS)) { Log(LOG_LEVEL_VERBOSE, "Skipping function '%s', because evaluation was turned off in the evaluator", fp->name); return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } else if (!EvalContextPromiseIsActive(ctx, caller)) { Log(LOG_LEVEL_VERBOSE, "Skipping function '%s', because it was excluded by classes", fp->name); return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } const FnCallType *fp_type = FnCallTypeGet(fp->name); if (!fp_type) { if (caller) { Log(LOG_LEVEL_ERR, "No such FnCall '%s' in promise '%s' near line %zd", fp->name, PromiseGetBundle(caller)->source_path, caller->offset.line); } else { Log(LOG_LEVEL_ERR, "No such FnCall '%s', context info unavailable", fp->name); } return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } Rlist *expargs = NewExpArgs(ctx, fp); if (UnresolvedArgs(expargs)) { DeleteExpArgs(expargs); return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } Rval cached_rval; if ((fp_type->options & FNCALL_OPTION_CACHED) && EvalContextFunctionCacheGet(ctx, fp, expargs, &cached_rval)) { return (FnCallResult) { FNCALL_SUCCESS, RvalCopy(cached_rval) }; } FnCallResult result = CallFunction(ctx, fp, expargs); if (result.status == FNCALL_FAILURE) { DeleteExpArgs(expargs); return (FnCallResult) { FNCALL_FAILURE, { FnCallCopy(fp), RVAL_TYPE_FNCALL } }; } if (fp_type->options & FNCALL_OPTION_CACHED) { EvalContextFunctionCachePut(ctx, fp, expargs, &result.rval); } DeleteExpArgs(expargs); return result; }