about summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--056recipe_header.cc6
-rw-r--r--057static_dispatch.cc18
-rw-r--r--070text.mu21
-rw-r--r--076stream.mu2
-rw-r--r--081print.mu2
5 files changed, 19 insertions, 30 deletions
diff --git a/056recipe_header.cc b/056recipe_header.cc
index a438054c..6797cab8 100644
--- a/056recipe_header.cc
+++ b/056recipe_header.cc
@@ -168,9 +168,11 @@ case NEXT_INGREDIENT_WITHOUT_TYPECHECKING: {
     ++current_call().next_ingredient_to_process;
   }
   else {
-    raise_error << maybe(current_recipe_name()) << "no ingredient to save in " << current_instruction().products.at(0).original_string << '\n' << end();
     products.resize(2);
-    products.at(0).push_back(0);
+    // pad the first product with sufficient zeros to match its type
+    long long int size = size_of(current_instruction().products.at(0));
+    for (long long int i = 0; i < size; ++i)
+      products.at(0).push_back(0);
     products.at(1).push_back(0);
   }
   break;
diff --git a/057static_dispatch.cc b/057static_dispatch.cc
index 2b48af10..bc699bcb 100644
--- a/057static_dispatch.cc
+++ b/057static_dispatch.cc
@@ -183,13 +183,8 @@ long long int variant_score(const instruction& inst, recipe_ordinal variant) {
     return -1;
   }
   const vector<reagent>& header_ingredients = get(Recipe, variant).ingredients;
-  if (SIZE(inst.ingredients) < SIZE(header_ingredients)) {
-    trace(9993, "transform") << "too few ingredients" << end();
-//?     cerr << "too few ingredients\n";
-    return -1;
-  }
 //?   cerr << "=== checking ingredients\n";
-  for (long long int i = 0; i < SIZE(header_ingredients); ++i) {
+  for (long long int i = 0; i < min(SIZE(inst.ingredients), SIZE(header_ingredients)); ++i) {
     if (!types_match(header_ingredients.at(i), inst.ingredients.at(i))) {
       trace(9993, "transform") << "mismatch: ingredient " << i << end();
 //?       cerr << "mismatch: ingredient " << i << '\n';
@@ -212,13 +207,8 @@ long long int variant_score(const instruction& inst, recipe_ordinal variant) {
     }
   }
 //?   cerr << "=== done checking ingredients\n";
-  if (SIZE(inst.products) > SIZE(get(Recipe, variant).products)) {
-    trace(9993, "transform") << "too few products" << end();
-//?     cerr << "too few products\n";
-    return -1;
-  }
   const vector<reagent>& header_products = get(Recipe, variant).products;
-  for (long long int i = 0; i < SIZE(inst.products); ++i) {
+  for (long long int i = 0; i < min(SIZE(header_products), SIZE(inst.products)); ++i) {
     if (is_dummy(inst.products.at(i))) continue;
     if (!types_match(header_products.at(i), inst.products.at(i))) {
       trace(9993, "transform") << "mismatch: product " << i << end();
@@ -242,8 +232,8 @@ long long int variant_score(const instruction& inst, recipe_ordinal variant) {
     }
   }
   // the greater the number of unused ingredients/products, the lower the score
-  return result - (SIZE(get(Recipe, variant).products)-SIZE(inst.products))
-                - (SIZE(inst.ingredients)-SIZE(get(Recipe, variant).ingredients));  // ok to go negative
+  return result - abs(SIZE(get(Recipe, variant).products)-SIZE(inst.products))
+                - abs(SIZE(inst.ingredients)-SIZE(get(Recipe, variant).ingredients));
 }
 
 :(scenario static_dispatch_disabled_on_headerless_definition)
diff --git a/070text.mu b/070text.mu
index 5de21e41..930b4587 100644
--- a/070text.mu
+++ b/070text.mu
@@ -431,10 +431,9 @@ scenario replace-character-in-text [
   ]
 ]
 
-recipe replace s:address:array:character, oldc:character, newc:character -> s:address:array:character [
+recipe replace s:address:array:character, oldc:character, newc:character, from:number/optional -> s:address:array:character [
   local-scope
   load-ingredients
-  from:number, _ <- next-ingredient  # default to 0
   len:number <- length *s
   i:number <- find-next s, oldc, from
   done?:boolean <- greater-or-equal i, len
@@ -773,9 +772,7 @@ scenario trim-newline-tab [
 
 recipe find-next text:address:array:character, pattern:character, idx:number -> next-index:number [
   local-scope
-  text:address:array:character <- next-ingredient
-  pattern:character <- next-ingredient
-  idx:number <- next-ingredient
+  load-ingredients
   len:number <- length *text
   {
     eof?:boolean <- greater-or-equal idx, len
@@ -1109,7 +1106,7 @@ recipe split s:address:array:character, delim:character -> result:address:array:
     end:number <- find-next s, delim, start
     # copy start..end into result[curr-result]
     dest:address:address:array:character <- index-address *result, curr-result
-    *dest <- copy s, start, end
+    *dest <- copy-range s, start, end
     # slide over to next slice
     start <- add end, 1
     curr-result <- add curr-result, 1
@@ -1215,9 +1212,9 @@ recipe split-first text:address:array:character, delim:character -> x:address:ar
     reply
   }
   idx:number <- find-next text, delim, 0
-  x:address:array:character <- copy text, 0, idx
+  x:address:array:character <- copy-range text, 0, idx
   idx <- add idx, 1
-  y:address:array:character <- copy text, idx, len
+  y:address:array:character <- copy-range text, idx, len
 ]
 
 scenario text-split-first [
@@ -1233,7 +1230,7 @@ scenario text-split-first [
   ]
 ]
 
-recipe copy buf:address:array:character, start:number, end:number -> result:address:array:character [
+recipe copy-range buf:address:array:character, start:number, end:number -> result:address:array:character [
   local-scope
   load-ingredients
   # if end is out of bounds, trim it
@@ -1260,7 +1257,7 @@ recipe copy buf:address:array:character, start:number, end:number -> result:addr
 scenario text-copy-copies-partial-text [
   run [
     1:address:array:character <- new [abc]
-    2:address:array:character <- copy 1:address:array:character, 1, 3
+    2:address:array:character <- copy-range 1:address:array:character, 1, 3
     3:array:character <- copy *2:address:array:character
   ]
   memory-should-contain [
@@ -1271,7 +1268,7 @@ scenario text-copy-copies-partial-text [
 scenario text-copy-out-of-bounds [
   run [
     1:address:array:character <- new [abc]
-    2:address:array:character <- copy 1:address:array:character, 2, 4
+    2:address:array:character <- copy-range 1:address:array:character, 2, 4
     3:array:character <- copy *2:address:array:character
   ]
   memory-should-contain [
@@ -1282,7 +1279,7 @@ scenario text-copy-out-of-bounds [
 scenario text-copy-out-of-bounds-2 [
   run [
     1:address:array:character <- new [abc]
-    2:address:array:character <- copy 1:address:array:character, 3, 3
+    2:address:array:character <- copy-range 1:address:array:character, 3, 3
     3:array:character <- copy *2:address:array:character
   ]
   memory-should-contain [
diff --git a/076stream.mu b/076stream.mu
index e72d4e86..be60d855 100644
--- a/076stream.mu
+++ b/076stream.mu
@@ -27,7 +27,7 @@ recipe read-line in:address:stream -> result:address:array:character, in:address
   idx:address:number <- get-address *in, index:offset
   s:address:array:character <- get *in, data:offset
   next-idx:number <- find-next s, 10/newline, *idx
-  result <- copy s, *idx, next-idx
+  result <- copy-range s, *idx, next-idx
   *idx <- add next-idx, 1  # skip newline
 ]
 
diff --git a/081print.mu b/081print.mu
index 445b6fa6..c0bc37ab 100644
--- a/081print.mu
+++ b/081print.mu
@@ -66,7 +66,7 @@ recipe clear-screen screen:address:screen -> screen:address:screen [
 
 recipe sync-screen screen:address:screen -> screen:address:screen [
   local-scope
-  screen:address:screen <- next-ingredient
+  load-ingredients
   {
     break-if screen
     sync-display