@@ -309,20 +309,52 @@ fn trans_static_method_callee(bcx: block,
309
309
}
310
310
311
311
fn method_from_methods(ms: ~[@ast::method], name: ast::ident)
312
- -> ast::def_id {
313
- local_def(option::get(vec:: find(ms, |m| m.ident == name)).id )
312
+ -> Option< ast::def_id> {
313
+ ms. find(|m| m.ident == name).map(|m| local_def(m.id) )
314
314
}
315
315
316
316
fn method_with_name(ccx: @crate_ctxt, impl_id: ast::def_id,
317
317
name: ast::ident) -> ast::def_id {
318
318
if impl_id.crate == ast::local_crate {
319
319
match ccx.tcx.items.get(impl_id.node) {
320
320
ast_map::node_item(@{node: ast::item_impl(_, _, _, ms), _}, _) => {
321
- method_from_methods(ms, name)
321
+ method_from_methods(ms, name).get()
322
322
}
323
323
ast_map::node_item(@{node:
324
324
ast::item_class(struct_def, _), _}, _) => {
325
- method_from_methods(struct_def.methods, name)
325
+ method_from_methods(struct_def.methods, name).get()
326
+ }
327
+ _ => fail ~" method_with_name"
328
+ }
329
+ } else {
330
+ csearch::get_impl_method(ccx.sess.cstore, impl_id, name)
331
+ }
332
+ }
333
+
334
+ fn method_with_name_or_default(ccx: @crate_ctxt, impl_id: ast::def_id,
335
+ name: ast::ident) -> ast::def_id {
336
+ if impl_id.crate == ast::local_crate {
337
+ match ccx.tcx.items.get(impl_id.node) {
338
+ ast_map::node_item(@{node: ast::item_impl(_, _, _, ms), _}, _) => {
339
+ let did = method_from_methods(ms, name);
340
+ if did.is_some() {
341
+ return did.get();
342
+ } else {
343
+ // Look for a default method
344
+ let pmm = ccx.tcx.provided_methods;
345
+ match pmm.find(impl_id) {
346
+ Some(pmis) => {
347
+ for pmis.each |pmi| {
348
+ if pmi.method_info.ident == name {
349
+ debug!(" XXX %?", pmi.method_info.did);
350
+ return pmi.method_info.did;
351
+ }
352
+ }
353
+ fail
354
+ }
355
+ None => fail
356
+ }
357
+ }
326
358
}
327
359
_ => fail ~" method_with_name"
328
360
}
@@ -333,10 +365,22 @@ fn method_with_name(ccx: @crate_ctxt, impl_id: ast::def_id,
333
365
334
366
fn method_ty_param_count(ccx: @crate_ctxt, m_id: ast::def_id,
335
367
i_id: ast::def_id) -> uint {
368
+ debug!(" mythod_ty_param_count: m_id: %?, i_id: %?", m_id, i_id);
336
369
if m_id.crate == ast::local_crate {
337
- match ccx.tcx.items.get(m_id.node) {
338
- ast_map::node_method(m, _, _) => vec::len(m.tps),
339
- _ => fail ~" method_ty_param_count"
370
+ match ccx.tcx.items.find(m_id.node) {
371
+ Some(ast_map::node_method(m, _, _)) => m.tps.len(),
372
+ None => {
373
+ match ccx.tcx.provided_method_sources.find(m_id) {
374
+ Some(source) => {
375
+ method_ty_param_count(ccx, source.method_id, source.impl_id)
376
+ }
377
+ None => fail
378
+ }
379
+ }
380
+ Some(ast_map::node_trait_method(@ast::provided(@m), _, _)) => {
381
+ m.tps.len()
382
+ }
383
+ e => fail fmt!(" method_ty_param_count %?", e)
340
384
}
341
385
} else {
342
386
csearch::get_type_param_count(ccx.sess.cstore, m_id) -
@@ -358,7 +402,8 @@ fn trans_monomorphized_callee(bcx: block,
358
402
typeck::vtable_static(impl_did, rcvr_substs, rcvr_origins) => {
359
403
let ccx = bcx.ccx();
360
404
let mname = ty::trait_methods(ccx.tcx, trait_id)[n_method].ident;
361
- let mth_id = method_with_name(bcx.ccx(), impl_did, mname);
405
+ let mth_id = method_with_name_or_default(
406
+ bcx.ccx(), impl_did, mname);
362
407
363
408
// obtain the `self` value:
364
409
let Result {bcx, val: llself_val} =
0 commit comments