From 7dcb37fc52090636d542f9d8d0d45a00a5c24c55 Mon Sep 17 00:00:00 2001 From: Ryan Lahfa Date: Wed, 27 Dec 2023 18:13:27 +0100 Subject: [PATCH] feat(tvix/eval): context-aware `substring` `substring` has a very funny behavior when it comes to empty strings, it propagates the context too, this is used in nixpkgs to attach context to strings without using any builtin: `lib.addContextFrom`. Change-Id: Id655356799b3485f7519b3d1914c630f9d8416c3 Reviewed-on: https://cl.tvl.fyi/c/depot/+/10448 Autosubmit: raitobezarius Reviewed-by: tazjin Tested-by: BuildkiteCI --- tvix/eval/src/builtins/mod.rs | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/tvix/eval/src/builtins/mod.rs b/tvix/eval/src/builtins/mod.rs index ee551bbaf..eaa1d1f98 100644 --- a/tvix/eval/src/builtins/mod.rs +++ b/tvix/eval/src/builtins/mod.rs @@ -1081,7 +1081,7 @@ mod pure_builtins { if x.is_catchable() { return Ok(x); } - let x = x.to_str()?; + let x = x.to_contextful_str()?; if beg < 0 { return Err(ErrorKind::IndexOutOfBounds { index: beg }); @@ -1092,7 +1092,7 @@ mod pure_builtins { // non-negative when the starting index is GTE the // string's length. if beg >= x.as_str().len() { - return Ok(Value::String("".into())); + return Ok(Value::String(NixString::new_inherit_context_from(&x, ""))); } let end = if len < 0 { @@ -1101,7 +1101,10 @@ mod pure_builtins { cmp::min(beg + (len as usize), x.as_str().len()) }; - Ok(Value::String(x.as_bytes()[beg..end].try_into()?)) + Ok(Value::String(NixString::new_inherit_context_from( + &x, + &x[beg..end], + ))) } #[builtin("tail")]