feat(tvix/eval): Give names to builtin arguments
Refactor the arguments of a Builtin to be a vec of a new BuiltinArgument struct, which contains the old strictness boolean and also a static `name` str - this is automatically determined via the ident for the corresponding function argument in the proc-macro case, and passed in in the cases where we're still manually calling Builtin::new. Currently this name is unused, but in the future this can be used as part of a documentation system for builtins. Change-Id: Ib9dadb15b69bf8c9ea1983a4f4f197294a2394a6 Reviewed-on: https://cl.tvl.fyi/c/depot/+/7204 Reviewed-by: tazjin <tazjin@tvl.su> Tested-by: BuildkiteCI
This commit is contained in:
parent
dad07a8bc0
commit
a1015ba1d7
6 changed files with 109 additions and 55 deletions
|
|
@ -25,6 +25,14 @@ use std::{
|
|||
pub trait BuiltinFn: Fn(Vec<Value>, &mut VM) -> Result<Value, ErrorKind> {}
|
||||
impl<F: Fn(Vec<Value>, &mut VM) -> Result<Value, ErrorKind>> BuiltinFn for F {}
|
||||
|
||||
/// Description of a single argument passed to a builtin
|
||||
pub struct BuiltinArgument {
|
||||
/// Whether the argument should be forced before the underlying builtin function is called
|
||||
pub strict: bool,
|
||||
/// The name of the argument, to be used in docstrings and error messages
|
||||
pub name: &'static str,
|
||||
}
|
||||
|
||||
/// Represents a single built-in function which directly executes Rust
|
||||
/// code that operates on a Nix value.
|
||||
///
|
||||
|
|
@ -40,10 +48,8 @@ impl<F: Fn(Vec<Value>, &mut VM) -> Result<Value, ErrorKind>> BuiltinFn for F {}
|
|||
#[derive(Clone)]
|
||||
pub struct Builtin {
|
||||
name: &'static str,
|
||||
/// Array reference that describes how many arguments there are (usually 1
|
||||
/// or 2) and whether they need to be forced. `true` causes the
|
||||
/// corresponding argument to be forced before `func` is called.
|
||||
strict_args: &'static [bool],
|
||||
/// Array of arguments to the builtin.
|
||||
arguments: &'static [BuiltinArgument],
|
||||
func: Rc<dyn BuiltinFn>,
|
||||
|
||||
/// Partially applied function arguments.
|
||||
|
|
@ -53,12 +59,12 @@ pub struct Builtin {
|
|||
impl Builtin {
|
||||
pub fn new<F: BuiltinFn + 'static>(
|
||||
name: &'static str,
|
||||
strict_args: &'static [bool],
|
||||
arguments: &'static [BuiltinArgument],
|
||||
func: F,
|
||||
) -> Self {
|
||||
Builtin {
|
||||
name,
|
||||
strict_args,
|
||||
arguments,
|
||||
func: Rc::new(func),
|
||||
partials: vec![],
|
||||
}
|
||||
|
|
@ -74,9 +80,9 @@ impl Builtin {
|
|||
pub fn apply(mut self, vm: &mut VM, arg: Value) -> Result<Value, ErrorKind> {
|
||||
self.partials.push(arg);
|
||||
|
||||
if self.partials.len() == self.strict_args.len() {
|
||||
for (idx, force) in self.strict_args.iter().enumerate() {
|
||||
if *force {
|
||||
if self.partials.len() == self.arguments.len() {
|
||||
for (idx, BuiltinArgument { strict, .. }) in self.arguments.iter().enumerate() {
|
||||
if *strict {
|
||||
self.partials[idx].force(vm)?;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue