@@ -82,22 +82,6 @@ fn new_ext_hash() -> ext_hash {
82
82
ret std:: map:: mk_hashmap :: < key , def > ( hash, eq) ;
83
83
}
84
84
85
- fn new_exp_hash ( ) -> exp_map {
86
- type key = { path: str , ns : namespace } ;
87
- fn hash ( v : key ) -> uint {
88
- ret str:: hash ( v. path ) +
89
- alt v. ns {
90
- ns_val ( _) { 1 u }
91
- ns_type { 2 u }
92
- ns_module { 3 u }
93
- } ;
94
- }
95
- fn eq ( v1 : key , v2 : key ) -> bool {
96
- ret str:: eq ( v1. path , v2. path ) && v1. ns == v2. ns ;
97
- }
98
- ret std:: map:: mk_hashmap :: < key , def > ( hash, eq) ;
99
- }
100
-
101
85
enum mod_index_entry {
102
86
mie_view_item( @ast:: view_item ) ,
103
87
mie_import_ident( node_id , codemap:: span ) ,
@@ -125,9 +109,9 @@ type indexed_mod = {
125
109
126
110
type def_map = hashmap < node_id , def > ;
127
111
type ext_map = hashmap < def_id , [ ident ] > ;
128
- type exp_map = hashmap < { path : str , ns : namespace } , def > ;
112
+ type exp_map = hashmap < str , @mutable [ def ] > ;
129
113
type impl_map = hashmap < node_id , iscopes > ;
130
- type impl_cache = hashmap < def_id , @[ @_impl ] > ;
114
+ type impl_cache = hashmap < def_id , option :: t < @[ @_impl ] > > ;
131
115
132
116
type env =
133
117
{ cstore : cstore:: cstore ,
@@ -168,7 +152,7 @@ fn resolve_crate(sess: session, amap: ast_map::map, crate: @ast::crate) ->
168
152
def_map: new_int_hash ( ) ,
169
153
ast_map: amap,
170
154
imports: new_int_hash ( ) ,
171
- exp_map: new_exp_hash ( ) ,
155
+ exp_map: new_str_hash ( ) ,
172
156
mod_map: new_int_hash ( ) ,
173
157
block_map: new_int_hash ( ) ,
174
158
ext_map: new_def_hash ( ) ,
@@ -1725,41 +1709,50 @@ fn check_exports(e: @env) {
1725
1709
let ( m, v, t) = ( lookup ( ns_module) ,
1726
1710
lookup ( ns_val ( ns_any_value) ) ,
1727
1711
lookup ( ns_type) ) ;
1728
- maybe_add_reexport ( e, path + ident, ns_module, m) ;
1729
- maybe_add_reexport ( e, path + ident, ns_val ( ns_any_value) , v) ;
1730
- maybe_add_reexport ( e, path + ident, ns_type, t) ;
1731
- ret is_some( m) || is_some ( v) || is_some ( t) ;
1732
- }
1733
-
1734
- fn maybe_add_reexport ( e : @env , path : str , ns : namespace ,
1735
- def : option:: t < def > ) {
1736
- if option:: is_some ( def) {
1737
- e. exp_map . insert ( { path: path, ns: ns} , option:: get ( def) ) ;
1712
+ let full_path = path + ident;
1713
+ maybe_add_reexport ( e, full_path, m) ;
1714
+ maybe_add_reexport ( e, full_path, v) ;
1715
+ maybe_add_reexport ( e, full_path, t) ;
1716
+ is_some ( m) || is_some ( v) || is_some ( t)
1717
+ }
1718
+
1719
+ fn maybe_add_reexport ( e : @env , path : str , def : option:: t < def > ) {
1720
+ alt def {
1721
+ some( def) {
1722
+ alt e. exp_map . find ( path) {
1723
+ some ( v) { * v += [ def] ; }
1724
+ none { e. exp_map . insert ( path, @mutable [ def] ) ; }
1725
+ }
1726
+ }
1727
+ _ { }
1738
1728
}
1739
1729
}
1740
1730
1741
- fn check_export ( e : @env , ident : str , val : @indexed_mod , vi : @view_item ) {
1731
+ fn check_export ( e : @env , ident : str , val : @indexed_mod ,
1732
+ vi : @view_item ) {
1733
+ let found_something = false ;
1734
+ let full_path = val. path + ident;
1742
1735
if val. index . contains_key ( ident) {
1736
+ found_something = true ;
1743
1737
let xs = val. index . get ( ident) ;
1744
1738
list:: iter ( xs) { |x|
1745
1739
alt x {
1746
1740
mie_import_ident( id, _) {
1747
1741
alt e. imports . get ( id) {
1748
1742
resolved ( v, t, m, _, rid, _) {
1749
- maybe_add_reexport ( e, val. path + rid,
1750
- ns_val ( ns_any_value) , v) ;
1751
- maybe_add_reexport ( e, val. path + rid, ns_type, t) ;
1752
- maybe_add_reexport ( e, val. path + rid, ns_module, m) ;
1743
+ maybe_add_reexport ( e, full_path, v) ;
1744
+ maybe_add_reexport ( e, full_path, t) ;
1745
+ maybe_add_reexport ( e, full_path, m) ;
1753
1746
}
1754
1747
_ { }
1755
1748
}
1756
1749
}
1757
1750
_ { }
1758
1751
}
1759
1752
}
1760
- } else if lookup_glob_any ( e , val , vi . span , val . path , ident ) {
1761
- // do nothing
1762
- } else {
1753
+ }
1754
+ found_something |= lookup_glob_any ( e , val , vi . span , val . path , ident ) ;
1755
+ if !found_something {
1763
1756
e. sess . span_warn ( vi. span ,
1764
1757
#fmt ( "exported item %s is not defined" , ident) ) ;
1765
1758
}
@@ -1849,40 +1842,52 @@ type iscopes = list<@[@_impl]>;
1849
1842
fn resolve_impls ( e : @env , c : @ast:: crate ) {
1850
1843
visit:: visit_crate ( * c, nil, visit:: mk_vt ( @{
1851
1844
visit_block: bind visit_block_with_impl_scope ( e, _, _, _) ,
1852
- visit_mod: bind visit_mod_with_impl_scope ( e, _, _, _, _) ,
1845
+ visit_mod: bind visit_mod_with_impl_scope ( e, _, _, _, _, _ ) ,
1853
1846
visit_expr: bind resolve_impl_in_expr ( e, _, _, _)
1854
1847
with * visit:: default_visitor ( )
1855
1848
} ) ) ;
1856
1849
}
1857
1850
1858
1851
fn find_impls_in_view_item ( e : env , vi : @ast:: view_item ,
1859
- & impls: [ @_impl ] , sc : iscopes ) {
1852
+ & impls: [ @_impl ] , sc : option:: t < iscopes > ) {
1853
+ fn lookup_imported_impls ( e : env , id : ast:: node_id ,
1854
+ act : fn ( @[ @_impl ] ) ) {
1855
+ alt e. imports . get ( id) {
1856
+ resolved ( _, _, _, is, _, _) { act ( is) ; }
1857
+ todo ( node_id, name, path, span, scopes) {
1858
+ resolve_import ( e, local_def ( node_id) , name, * path, span,
1859
+ scopes) ;
1860
+ alt e. imports . get ( id) {
1861
+ resolved ( _, _, _, is, _, _) { act ( is) ; }
1862
+ }
1863
+ }
1864
+ _ { }
1865
+ }
1866
+ }
1860
1867
alt vi. node {
1861
1868
ast:: view_item_import ( name, pt, id) {
1862
1869
let found = [ ] ;
1863
1870
if vec:: len ( * pt) == 1 u {
1864
- list:: iter ( sc) { |level|
1865
- if vec:: len ( found) > 0 u { ret; }
1866
- for imp in * level {
1867
- if imp. ident == pt[ 0 ] {
1868
- found += [ @{ ident: name with * imp} ] ;
1871
+ option:: may ( sc) { |sc|
1872
+ list:: iter ( sc) { |level|
1873
+ if vec:: len ( found) > 0 u { ret; }
1874
+ for imp in * level {
1875
+ if imp. ident == pt[ 0 ] {
1876
+ found += [ @{ ident: name with * imp} ] ;
1877
+ }
1869
1878
}
1879
+ if vec:: len ( found) > 0 u { impls += found; }
1870
1880
}
1871
- if vec:: len ( found) > 0 u { impls += found; }
1872
1881
}
1873
1882
} else {
1874
- alt e. imports . get ( id) {
1875
- resolved ( _, _, _, is, _, _) {
1883
+ lookup_imported_impls( e, id) { |is|
1876
1884
for i in * is { impls += [ @{ ident: name with * i} ] ; }
1877
- }
1878
1885
}
1879
1886
}
1880
1887
}
1881
1888
ast:: view_item_import_from ( base, names, _) {
1882
1889
for nm in names {
1883
- alt e. imports . get ( nm. node . id ) {
1884
- resolved ( _, _, _, is, _, _) { impls += * is; }
1885
- }
1890
+ lookup_imported_impls ( e, nm. node . id ) { |is| impls += * is; }
1886
1891
}
1887
1892
}
1888
1893
ast:: view_item_import_glob ( ids, id) {
@@ -1922,34 +1927,45 @@ fn find_impls_in_item(e: env, i: @ast::item, &impls: [@_impl],
1922
1927
}
1923
1928
}
1924
1929
1930
+ fn find_impls_in_mod_by_id ( e : env , defid : def_id , & impls: [ @_impl ] ,
1931
+ name : option:: t < ident > ) {
1932
+ let cached;
1933
+ alt e. impl_cache . find ( defid) {
1934
+ some ( some ( v) ) { cached = v; }
1935
+ some ( none) { ret; }
1936
+ none {
1937
+ e. impl_cache . insert ( defid, none) ;
1938
+ cached = if defid. crate == ast:: local_crate {
1939
+ let tmp = [ ] ;
1940
+ let md = option:: get ( e. mod_map . get ( defid. node ) . m ) ;
1941
+ for vi in md. view_items {
1942
+ find_impls_in_view_item ( e, vi, tmp, none) ;
1943
+ }
1944
+ for i in md. items {
1945
+ find_impls_in_item ( e, i, tmp, none, none) ;
1946
+ }
1947
+ @vec:: filter ( tmp) { |i| is_exported ( e, i. ident , md) }
1948
+ } else {
1949
+ csearch:: get_impls_for_mod ( e. sess . cstore , defid, none)
1950
+ } ;
1951
+ e. impl_cache . insert ( defid, some ( cached) ) ;
1952
+ }
1953
+ }
1954
+ alt name {
1955
+ some( n) {
1956
+ for im in * cached {
1957
+ if n == im. ident { impls += [ im] ; }
1958
+ }
1959
+ }
1960
+ _ { impls += * cached; }
1961
+ }
1962
+ }
1963
+
1925
1964
fn find_impls_in_mod( e : env , m : def , & impls: [ @_impl ] ,
1926
1965
name : option:: t < ident > ) {
1927
1966
alt m {
1928
1967
ast : : def_mod ( defid) {
1929
- let cached;
1930
- alt e. impl_cache . find ( defid) {
1931
- some ( v) { cached = v; }
1932
- none {
1933
- cached = if defid. crate == ast:: local_crate {
1934
- let tmp = [ ] ;
1935
- for i in option:: get ( e. mod_map . get ( defid. node ) . m ) . items {
1936
- find_impls_in_item ( e, i, tmp, none, none) ;
1937
- }
1938
- @tmp
1939
- } else {
1940
- csearch:: get_impls_for_mod ( e. sess . cstore , defid, none)
1941
- } ;
1942
- e. impl_cache . insert ( defid, cached) ;
1943
- }
1944
- }
1945
- alt name {
1946
- some( n) {
1947
- for im in * cached {
1948
- if n == im. ident { impls += [ im] ; }
1949
- }
1950
- }
1951
- _ { impls += * cached; }
1952
- }
1968
+ find_impls_in_mod_by_id ( e, defid, impls, name) ;
1953
1969
}
1954
1970
_ { }
1955
1971
}
@@ -1959,7 +1975,7 @@ fn visit_block_with_impl_scope(e: @env, b: ast::blk, sc: iscopes,
1959
1975
v : vt < iscopes > ) {
1960
1976
let impls = [ ] ;
1961
1977
for vi in b. node . view_items {
1962
- find_impls_in_view_item ( * e, vi, impls, sc ) ;
1978
+ find_impls_in_view_item ( * e, vi, impls, some ( sc ) ) ;
1963
1979
}
1964
1980
for st in b. node . stmts {
1965
1981
alt st. node {
@@ -1973,12 +1989,17 @@ fn visit_block_with_impl_scope(e: @env, b: ast::blk, sc: iscopes,
1973
1989
visit:: visit_block ( b, sc, v) ;
1974
1990
}
1975
1991
1976
- fn visit_mod_with_impl_scope ( e : @env , m : ast:: _mod , s : span , sc : iscopes ,
1977
- v : vt < iscopes > ) {
1992
+ fn visit_mod_with_impl_scope ( e : @env , m : ast:: _mod , s : span , id : node_id ,
1993
+ sc : iscopes , v : vt < iscopes > ) {
1978
1994
let impls = [ ] ;
1979
- for vi in m. view_items { find_impls_in_view_item ( * e, vi, impls, sc) ; }
1995
+ for vi in m. view_items {
1996
+ find_impls_in_view_item ( * e, vi, impls, some ( sc) ) ;
1997
+ }
1980
1998
for i in m. items { find_impls_in_item ( * e, i, impls, none, none) ; }
1981
- visit:: visit_mod ( m, s, vec:: len ( impls) > 0 u ? cons ( @impls, @sc) : sc, v) ;
1999
+ let impls = @impls;
2000
+ visit:: visit_mod ( m, s, id,
2001
+ vec:: len ( * impls) > 0 u ? cons ( impls, @sc) : sc, v) ;
2002
+ e. impl_map . insert ( id, cons ( impls, @nil) ) ;
1982
2003
}
1983
2004
1984
2005
fn resolve_impl_in_expr ( e : @env , x : @ast:: expr , sc : iscopes , v : vt < iscopes > ) {
0 commit comments