about summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorKartik K. Agaram <vc@akkartik.com>2017-12-07 15:59:48 -0800
committerKartik K. Agaram <vc@akkartik.com>2017-12-07 16:00:02 -0800
commit07de3e9536fc1f3fc8f8f77f833c4730b6de1b7d (patch)
tree77278540a072945823364e0abf80d134a98ecb57
parentba2729b2011da0c7e644d1c25a5ff75fca6bb848 (diff)
downloadmu-07de3e9536fc1f3fc8f8f77f833c4730b6de1b7d.tar.gz
4151 - specializing calls returning continuations
-rw-r--r--072recipe.cc13
-rw-r--r--076continuation.cc19
2 files changed, 30 insertions, 2 deletions
diff --git a/072recipe.cc b/072recipe.cc
index d05e8575..eaf1baf3 100644
--- a/072recipe.cc
+++ b/072recipe.cc
@@ -205,7 +205,17 @@ def f x:point -> y:point [
 +error: main: product 0 has the wrong type at '2:num <- call {1: (recipe point -> point)}, 34'
 
 :(before "End resolve_ambiguous_call(r, index, inst, caller_recipe) Special-cases")
-if (inst.name == "call" && !inst.ingredients.empty() && inst.ingredients.at(0).type && inst.ingredients.at(0).type->atom && inst.ingredients.at(0).type->name == "recipe-literal") {
+if (inst.name == "call" && first_ingredient_is_recipe_literal(inst)) {
+  resolve_indirect_ambiguous_call(r, index, inst, caller_recipe);
+  return;
+}
+:(code)
+bool first_ingredient_is_recipe_literal(const instruction& inst) {
+  if (inst.ingredients.empty()) return false;
+  const reagent& ingredient = inst.ingredients.at(0);
+  return ingredient.type && ingredient.type->atom && ingredient.type->name == "recipe-literal";
+}
+void resolve_indirect_ambiguous_call(const recipe_ordinal r, int index, instruction& inst, const recipe& caller_recipe) {
   instruction inst2;
   inst2.name = inst.ingredients.at(0).name;
   for (int i = /*skip recipe*/1;  i < SIZE(inst.ingredients);  ++i)
@@ -215,7 +225,6 @@ if (inst.name == "call" && !inst.ingredients.empty() && inst.ingredients.at(0).t
   resolve_ambiguous_call(r, index, inst2, caller_recipe);
   inst.ingredients.at(0).name = inst2.name;
   inst.ingredients.at(0).set_value(get(Recipe_ordinal, inst2.name));
-  return;
 }
 
 :(after "Transform.push_back(check_instruction)")
diff --git a/076continuation.cc b/076continuation.cc
index df6d0e67..94c3f97a 100644
--- a/076continuation.cc
+++ b/076continuation.cc
@@ -260,6 +260,25 @@ def g [
 # ..even though we never called the continuation
 -app: continuation called
 
+//: Allow shape-shifting recipes to return continuations.
+
+:(scenario call_shape_shifting_recipe_with_continuation_mark)
+def main [
+  1:num <- call-with-continuation-mark f, 34
+]
+def f x:_elem -> y:_elem [
+  local-scope
+  load-ingredients
+  y <- copy x
+]
++mem: storing 34 in location 1
+
+:(before "End resolve_ambiguous_call(r, index, inst, caller_recipe) Special-cases")
+if (inst.name == "call-with-continuation-mark" && first_ingredient_is_recipe_literal(inst)) {
+  resolve_indirect_ambiguous_call(r, index, inst, caller_recipe);
+  return;
+}
+
 //: Ensure that the presence of a continuation keeps its stack frames from being reclaimed.
 
 :(scenario continuations_preserve_local_scopes)
ate files' href='/gbmor/getwtxt/commit/svc/sqlite.go?h=v0.4.14&id=a5a32e7a317dd5cf156e52a71d7be432d0594bf7'>a5a32e7 ^
a5a32e7 ^


40357b7 ^
a5a32e7 ^
a5a32e7 ^







d20ad73 ^

a5a32e7 ^
18fc34c ^
a5a32e7 ^




18fc34c ^
a5a32e7 ^
a5a32e7 ^
a5a32e7 ^







a5a32e7 ^






37142b5 ^

a5a32e7 ^




a5a32e7 ^


a5a32e7 ^
a5a32e7 ^
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155