Skip to content

Commit 68c76b3

Browse files
committed
---
yaml --- r: 2177 b: refs/heads/master c: bc50a3b h: refs/heads/master i: 2175: 4dda144 v: v3
1 parent a6ff75b commit 68c76b3

File tree

2 files changed

+64
-4
lines changed

2 files changed

+64
-4
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: 7596fcfba7e524977f42f24933173414f3e23cd1
2+
refs/heads/master: bc50a3ba44293a1913e3fd7c1f7db094f9f55cdc

trunk/src/comp/middle/typeck.rs

Lines changed: 63 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -48,12 +48,18 @@ tag any_item {
4848

4949
type ty_item_table = hashmap[ast.def_id,any_item];
5050

51+
type unify_cache_entry = tup(@ty.t,@ty.t,vec[mutable @ty.t]);
52+
type unify_cache = hashmap[unify_cache_entry,ty.unify_result];
53+
5154
type crate_ctxt = rec(session.session sess,
5255
ty.type_cache type_cache,
5356
@ty_item_table item_items,
5457
vec[ast.obj_field] obj_fields,
5558
option.t[ast.def_id] this_obj,
56-
mutable int next_var_id);
59+
mutable int next_var_id,
60+
unify_cache unify_cache,
61+
mutable uint cache_hits,
62+
mutable uint cache_misses);
5763

5864
type fn_ctxt = rec(@ty.t ret_ty,
5965
@ty_table locals,
@@ -842,6 +848,14 @@ mod Unify {
842848

843849
fn with_params(@fn_ctxt fcx, @ty.t expected, @ty.t actual,
844850
vec[mutable @ty.t] param_substs) -> ty.unify_result {
851+
auto cache_key = tup(expected, actual, param_substs);
852+
if (fcx.ccx.unify_cache.contains_key(cache_key)) {
853+
fcx.ccx.cache_hits += 1u;
854+
ret fcx.ccx.unify_cache.get(cache_key);
855+
}
856+
857+
fcx.ccx.cache_misses += 1u;
858+
845859
obj unify_handler(@fn_ctxt fcx, vec[mutable @ty.t] param_substs) {
846860
fn resolve_local(ast.def_id id) -> option.t[@ty.t] {
847861
alt (fcx.locals.find(id)) {
@@ -898,7 +912,9 @@ mod Unify {
898912

899913

900914
auto handler = unify_handler(fcx, param_substs);
901-
ret ty.unify(expected, actual, handler);
915+
auto result = ty.unify(expected, actual, handler);
916+
fcx.ccx.unify_cache.insert(cache_key, result);
917+
ret result;
902918
}
903919
}
904920

@@ -2699,19 +2715,59 @@ fn update_obj_fields(&@crate_ctxt ccx, @ast.item i) -> @crate_ctxt {
26992715
}
27002716

27012717

2718+
// Utilities for the unification cache
2719+
2720+
fn hash_unify_cache_entry(&unify_cache_entry uce) -> uint {
2721+
auto h = ty.hash_ty(uce._0);
2722+
h += h << 5u + ty.hash_ty(uce._1);
2723+
2724+
auto i = 0u;
2725+
auto tys_len = _vec.len[mutable @ty.t](uce._2);
2726+
while (i < tys_len) {
2727+
h += h << 5u + ty.hash_ty(uce._2.(i));
2728+
i += 1u;
2729+
}
2730+
2731+
ret h;
2732+
}
2733+
2734+
fn eq_unify_cache_entry(&unify_cache_entry a, &unify_cache_entry b) -> bool {
2735+
if (!ty.eq_ty(a._0, b._0) || !ty.eq_ty(a._1, b._1)) { ret false; }
2736+
2737+
auto i = 0u;
2738+
auto tys_len = _vec.len[mutable @ty.t](a._2);
2739+
if (_vec.len[mutable @ty.t](b._2) != tys_len) { ret false; }
2740+
2741+
while (i < tys_len) {
2742+
if (!ty.eq_ty(a._2.(i), b._2.(i))) { ret false; }
2743+
i += 1u;
2744+
}
2745+
2746+
ret true;
2747+
}
2748+
2749+
27022750
type typecheck_result = tup(@ast.crate, ty.type_cache);
27032751

27042752
fn check_crate(session.session sess, @ast.crate crate) -> typecheck_result {
27052753
auto result = collect_item_types(sess, crate);
27062754

27072755
let vec[ast.obj_field] fields = vec();
27082756

2757+
auto hasher = hash_unify_cache_entry;
2758+
auto eqer = eq_unify_cache_entry;
2759+
auto unify_cache =
2760+
map.mk_hashmap[unify_cache_entry,ty.unify_result](hasher, eqer);
2761+
27092762
auto ccx = @rec(sess=sess,
27102763
type_cache=result._1,
27112764
item_items=result._2,
27122765
obj_fields=fields,
27132766
this_obj=none[ast.def_id],
2714-
mutable next_var_id=0);
2767+
mutable next_var_id=0,
2768+
unify_cache=unify_cache,
2769+
mutable cache_hits=0u,
2770+
mutable cache_misses=0u);
27152771

27162772
auto fld = fold.new_identity_fold[@crate_ctxt]();
27172773

@@ -2721,6 +2777,10 @@ fn check_crate(session.session sess, @ast.crate crate) -> typecheck_result {
27212777
with *fld);
27222778

27232779
auto crate_1 = fold.fold_crate[@crate_ctxt](ccx, fld, result._0);
2780+
2781+
log #fmt("cache hit rate: %u/%u", ccx.cache_hits,
2782+
ccx.cache_hits + ccx.cache_misses);
2783+
27242784
ret tup(crate_1, ccx.type_cache);
27252785
}
27262786

0 commit comments

Comments
 (0)