Skip to content

Commit 454d47d

Browse files
committed
---
yaml --- r: 1104 b: refs/heads/master c: 51782d2 h: refs/heads/master v: v3
1 parent 86a3aaa commit 454d47d

File tree

2 files changed

+84
-64
lines changed

2 files changed

+84
-64
lines changed

[refs]

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,2 +1,2 @@
11
---
2-
refs/heads/master: a6c6e8679e2a04624be710c00828bd59d1f4cc3b
2+
refs/heads/master: 51782d2c21b275b8c9fcbf6cf05222d24aa1ada9

trunk/src/comp/middle/typeck.rs

Lines changed: 83 additions & 63 deletions
Original file line numberDiff line numberDiff line change
@@ -261,75 +261,26 @@ fn ty_to_str(&@ty typ) -> str {
261261

262262
// Replaces parameter types inside a type with type variables.
263263
fn generalize_ty(@crate_ctxt cx, @ty t) -> @ty {
264-
fn rewrap(@ty orig, &sty new) -> @ty {
265-
ret @rec(struct=new, mut=orig.mut, cname=orig.cname);
266-
}
267-
268-
fn recur(@crate_ctxt cx, @ty t,
269-
&hashmap[ast.def_id,@ty] ty_params_to_ty_vars) -> @ty {
270-
alt (t.struct) {
271-
case (ty_box(?subty)) {
272-
auto new_subty = recur(cx, subty, ty_params_to_ty_vars);
273-
ret rewrap(t, ty_box(new_subty));
274-
}
275-
case (ty_vec(?subty)) {
276-
auto new_subty = recur(cx, subty, ty_params_to_ty_vars);
277-
ret rewrap(t, ty_vec(new_subty));
278-
}
279-
case (ty_tup(?subtys)) {
280-
let vec[@ty] new_subtys = vec();
281-
for (@ty subty in subtys) {
282-
new_subtys += vec(recur(cx, subty, ty_params_to_ty_vars));
283-
}
284-
ret rewrap(t, ty_tup(new_subtys));
285-
}
286-
case (ty_rec(?fields)) {
287-
let vec[field] new_fields = vec();
288-
for (field fld in fields) {
289-
auto new_ty = recur(cx, fld.ty, ty_params_to_ty_vars);
290-
new_fields += vec(rec(ident=fld.ident, ty=new_ty));
291-
}
292-
ret rewrap(t, ty_rec(new_fields));
293-
}
294-
case (ty_fn(?args, ?ret_ty)) {
295-
let vec[arg] new_args = vec();
296-
for (arg a in args) {
297-
auto new_ty = recur(cx, a.ty, ty_params_to_ty_vars);
298-
new_args += vec(rec(mode=a.mode, ty=new_ty));
299-
}
300-
auto new_ret_ty = recur(cx, ret_ty, ty_params_to_ty_vars);
301-
ret rewrap(t, ty_fn(new_args, new_ret_ty));
302-
}
303-
case (ty_obj(?methods)) {
304-
let vec[method] new_methods = vec();
305-
for (method m in methods) {
306-
let vec[arg] new_args = vec();
307-
for (arg a in m.inputs) {
308-
auto new_ty = recur(cx, a.ty, ty_params_to_ty_vars);
309-
new_args += vec(rec(mode=a.mode, ty=new_ty));
264+
state obj ty_generalizer(@crate_ctxt cx,
265+
@hashmap[ast.def_id,@ty] ty_params_to_ty_vars) {
266+
fn fold_simple_ty(@ty t) -> @ty {
267+
alt (t.struct) {
268+
case (ty_param(?pid)) {
269+
if (ty_params_to_ty_vars.contains_key(pid)) {
270+
ret ty_params_to_ty_vars.get(pid);
310271
}
311-
auto new_rty = recur(cx, m.output, ty_params_to_ty_vars);
312-
new_methods += vec(rec(ident=m.ident, inputs=new_args,
313-
output=new_rty));
314-
}
315-
ret rewrap(t, ty_obj(new_methods));
316-
}
317-
case (ty_param(?pid)) {
318-
if (ty_params_to_ty_vars.contains_key(pid)) {
319-
ret ty_params_to_ty_vars.get(pid);
272+
auto var_ty = next_ty_var(cx);
273+
ty_params_to_ty_vars.insert(pid, var_ty);
274+
ret var_ty;
320275
}
321-
auto var_ty = next_ty_var(cx);
322-
ty_params_to_ty_vars.insert(pid, var_ty);
323-
ret var_ty;
276+
case (_) { /* fall through */ }
324277
}
325-
case (_) { /* fall through */ }
278+
ret t;
326279
}
327-
328-
ret t;
329280
}
330281

331-
auto ty_params_to_ty_vars = common.new_def_hash[@ty]();
332-
ret recur(cx, t, ty_params_to_ty_vars);
282+
auto generalizer = ty_generalizer(cx, @common.new_def_hash[@ty]());
283+
ret fold_ty(generalizer, t);
333284
}
334285

335286
// Parses the programmer's textual representation of a type into our internal
@@ -779,6 +730,75 @@ fn is_lval(@ast.expr expr) -> bool {
779730
}
780731
}
781732

733+
// Type folds
734+
735+
type ty_fold = state obj {
736+
fn fold_simple_ty(@ty ty) -> @ty;
737+
};
738+
739+
fn fold_ty(ty_fold fld, @ty t) -> @ty {
740+
fn rewrap(@ty orig, &sty new) -> @ty {
741+
ret @rec(struct=new, mut=orig.mut, cname=orig.cname);
742+
}
743+
744+
alt (t.struct) {
745+
case (ty_nil) { ret fld.fold_simple_ty(t); }
746+
case (ty_bool) { ret fld.fold_simple_ty(t); }
747+
case (ty_int) { ret fld.fold_simple_ty(t); }
748+
case (ty_uint) { ret fld.fold_simple_ty(t); }
749+
case (ty_machine(_)) { ret fld.fold_simple_ty(t); }
750+
case (ty_char) { ret fld.fold_simple_ty(t); }
751+
case (ty_str) { ret fld.fold_simple_ty(t); }
752+
case (ty_tag(_)) { ret fld.fold_simple_ty(t); }
753+
case (ty_box(?subty)) {
754+
ret rewrap(t, ty_box(fold_ty(fld, subty)));
755+
}
756+
case (ty_vec(?subty)) {
757+
ret rewrap(t, ty_vec(fold_ty(fld, subty)));
758+
}
759+
case (ty_tup(?subtys)) {
760+
let vec[@ty] new_subtys = vec();
761+
for (@ty subty in subtys) {
762+
new_subtys += vec(fold_ty(fld, subty));
763+
}
764+
ret rewrap(t, ty_tup(new_subtys));
765+
}
766+
case (ty_rec(?fields)) {
767+
let vec[field] new_fields = vec();
768+
for (field fl in fields) {
769+
auto new_ty = fold_ty(fld, fl.ty);
770+
new_fields += vec(rec(ident=fl.ident, ty=new_ty));
771+
}
772+
ret rewrap(t, ty_rec(new_fields));
773+
}
774+
case (ty_fn(?args, ?ret_ty)) {
775+
let vec[arg] new_args = vec();
776+
for (arg a in args) {
777+
auto new_ty = fold_ty(fld, a.ty);
778+
new_args += vec(rec(mode=a.mode, ty=new_ty));
779+
}
780+
ret rewrap(t, ty_fn(new_args, fold_ty(fld, ret_ty)));
781+
}
782+
case (ty_obj(?methods)) {
783+
let vec[method] new_methods = vec();
784+
for (method m in methods) {
785+
let vec[arg] new_args = vec();
786+
for (arg a in m.inputs) {
787+
new_args += vec(rec(mode=a.mode, ty=fold_ty(fld, a.ty)));
788+
}
789+
new_methods += vec(rec(ident=m.ident, inputs=new_args,
790+
output=fold_ty(fld, m.output)));
791+
}
792+
ret rewrap(t, ty_obj(new_methods));
793+
}
794+
case (ty_var(_)) { ret fld.fold_simple_ty(t); }
795+
case (ty_local(_)) { ret fld.fold_simple_ty(t); }
796+
case (ty_param(_)) { ret fld.fold_simple_ty(t); }
797+
}
798+
799+
ret t;
800+
}
801+
782802
// Type utilities
783803

784804
// FIXME: remove me when == works on these tags.

0 commit comments

Comments
 (0)