Skip to content

Commit

Permalink
refactor: use a slice to pass function arguments
Browse files Browse the repository at this point in the history
This should allow use a temporary vec/slice when calling fuctions, which
will allow us to release memory for function calls that will not be
needed in the result. We are hoping this will lower our overall memory
footprint.
  • Loading branch information
aesterline committed Jun 23, 2024
1 parent 7ab1542 commit 1dfcef9
Show file tree
Hide file tree
Showing 4 changed files with 173 additions and 162 deletions.
54 changes: 25 additions & 29 deletions src/evaluator.rs
Original file line number Diff line number Diff line change
Expand Up @@ -310,11 +310,10 @@ impl<'a> Evaluator<'a> {
if group.index != index {
return Err(Error::D1009MultipleKeys(char_index, key.to_string()));
}
let args = Value::array_with_capacity(self.arena, 2, ArrayFlags::empty());
args.push(group.data);
args.push(item);
group.data =
fn_append(self.fn_context("append", char_index, input, frame), args)?;
group.data = fn_append(
self.fn_context("append", char_index, input, frame),
&[group.data, item],
)?;
}
hash_map::Entry::Vacant(entry) => {
entry.insert(Group { data: item, index });
Expand Down Expand Up @@ -363,11 +362,10 @@ impl<'a> Evaluator<'a> {
}
for i in 1..tuple_stream.len() {
for (key, value) in tuple_stream[i].entries() {
let args = Value::array_with_capacity(self.arena, 2, ArrayFlags::empty());
args.push(result.get_entry(&key[..]));
args.push(value);
let new_value =
fn_append(self.fn_context("append", char_index, input, frame), args)?;
let new_value = fn_append(
self.fn_context("append", char_index, input, frame),
&[result.get_entry(&key[..]), value],
)?;
result.insert(key, new_value);
}
}
Expand Down Expand Up @@ -543,7 +541,7 @@ impl<'a> Evaluator<'a> {
result.push_str(
&fn_string(
self.fn_context("string", node.char_index, input, frame),
Value::wrap_in_array(self.arena, lhs, ArrayFlags::empty()),
&[lhs],
)?
.as_str(),
);
Expand All @@ -552,7 +550,7 @@ impl<'a> Evaluator<'a> {
result.push_str(
&fn_string(
self.fn_context("string", node.char_index, input, frame),
Value::wrap_in_array(self.arena, rhs, ArrayFlags::empty()),
&[rhs],
)?
.as_str(),
);
Expand Down Expand Up @@ -595,25 +593,19 @@ impl<'a> Evaluator<'a> {
frame,
)?;

let args = Value::array_with_capacity(self.arena, 2, ArrayFlags::empty());
args.push(lhs);
args.push(rhs);

Ok(self.apply_function(
lhs_ast.char_index,
Value::undefined(),
chain,
args,
&[lhs, rhs],
frame,
)?)
} else {
let args = Value::array_with_capacity(self.arena, 1, ArrayFlags::empty());
args.push(lhs);
Ok(self.apply_function(
rhs_ast.char_index,
Value::undefined(),
rhs,
args,
&[lhs],
frame,
)?)
}
Expand Down Expand Up @@ -730,7 +722,7 @@ impl<'a> Evaluator<'a> {
result = Value::wrap_in_array(
self.arena,
result,
flags.clone() | ArrayFlags::SEQUENCE | ArrayFlags::SINGLETON,
flags | ArrayFlags::SEQUENCE | ArrayFlags::SINGLETON,
);
}
result = result.clone_array_with_flags(self.arena, flags | ArrayFlags::SINGLETON);
Expand Down Expand Up @@ -1209,8 +1201,7 @@ impl<'a> Evaluator<'a> {
}
}

let evaluated_args =
Value::array_with_capacity(self.arena, args.len(), ArrayFlags::empty());
let mut evaluated_args = Vec::with_capacity(args.len());

if let Some(context) = context {
evaluated_args.push(context);
Expand All @@ -1225,7 +1216,7 @@ impl<'a> Evaluator<'a> {
proc.char_index,
input,
evaluated_proc,
evaluated_args,
&evaluated_args,
frame,
)?;

Expand All @@ -1249,16 +1240,15 @@ impl<'a> Evaluator<'a> {
} = body.kind
{
let next = self.evaluate(proc, lambda_input, lambda_frame)?;
let evaluated_args =
Value::array_with_capacity(self.arena, args.len(), ArrayFlags::empty());
let mut evaluated_args = Vec::with_capacity(args.len());

for arg in args {
let arg = self.evaluate(arg, lambda_input, lambda_frame)?;
evaluated_args.push(arg);
}

result =
self.apply_function(proc.char_index, input, next, evaluated_args, frame)?;
self.apply_function(proc.char_index, input, next, &evaluated_args, frame)?;
} else {
unreachable!()
}
Expand All @@ -1275,7 +1265,7 @@ impl<'a> Evaluator<'a> {
char_index: usize,
input: &'a Value<'a>,
evaluated_proc: &'a Value<'a>,
evaluated_args: &'a Value<'a>,
evaluated_args: &[&'a Value<'a>],
frame: &Frame<'a>,
) -> Result<&'a Value<'a>> {
match evaluated_proc {
Expand All @@ -1295,7 +1285,13 @@ impl<'a> Evaluator<'a> {
// Bind the arguments to their respective names
for (index, arg) in args.iter().enumerate() {
if let AstKind::Var(ref name) = arg.kind {
frame.bind(name, evaluated_args.get_member(index));
frame.bind(
name,
evaluated_args
.get(index)
.copied()
.unwrap_or_else(Value::undefined),
);
} else {
unreachable!()
}
Expand Down
Loading

0 comments on commit 1dfcef9

Please sign in to comment.