Resolve: more preperation work for parallelizing the import resolution loop#159440
Resolve: more preperation work for parallelizing the import resolution loop#159440LorrensP-2158466 wants to merge 1 commit into
Conversation
This comment has been minimized.
This comment has been minimized.
0d9f4a2 to
aa051d9
Compare
|
I double-checked with @rustbot ready |
This comment has been minimized.
This comment has been minimized.
…par_slice`. Currently it is all still single threaded, but almost everything needed to make the loop use multithreaded code is done in this commit. For performance reasons we do the resolution now in place instead of recollecting the indeterminate imports ([see benchmark pr](rust-lang#159387) and pr of this commit). With the accompanying changes to make datastructures concurrent: - populating external resolution tables now use `Once` to ensure only 1 thread builds the table and all others wait if they need it - implement `DynSync`/`DynSend` for `RefOrMut` and `CmCell` so it is allowed to use the `par_slice` function. `Cache(Ref)Cells` are not tackled yet because they are not needed here (and require extra work).
aa051d9 to
2e9c9d2
Compare
| &self, | ||
| def_id: DefId, | ||
| map_lock: &mut RefMut<'_, FxIndexMap<DefId, ExternModule<'ra>>>, | ||
| ) -> Option<Module<'ra>> { |
There was a problem hiding this comment.
| ) -> Option<Module<'ra>> { | |
| ) -> Option<ExternModule<'ra>> { |
| while let MacroRulesScope::Invocation(invoc_id) = scope { | ||
| if let Some(next) = self.output_macro_rules_scopes.get(&invoc_id) { | ||
| scope = next.get(); | ||
| macro_rules_scope.set(scope); |
There was a problem hiding this comment.
| macro_rules_scope.set(scope); | |
| macro_rules_scope.set(next.get()); |
Does the RwLock version really not work in the nicer way, like before?
| indeterminate_count = 0; | ||
| let mut resolutions = Vec::new(); | ||
|
|
||
| let mut to_resolve_imports = mem::take(&mut self.indeterminate_imports); |
There was a problem hiding this comment.
| let mut to_resolve_imports = mem::take(&mut self.indeterminate_imports); | |
| let mut imports_to_resolve = mem::take(&mut self.indeterminate_imports); |
| let (new_resolution, import_indeterminate_count) = | ||
| cm_resolver.reborrow_ref().resolve_import(*import); | ||
| *resolution = new_resolution; | ||
| *indeterminate_count = import_indeterminate_count |
There was a problem hiding this comment.
| *indeterminate_count = import_indeterminate_count | |
| (*resolution, *indeterminate_count) = cm_resolver.reborrow_ref().resolve_import(*import); |
This should actually work (it's a destructuring assignment).
| self.write_import_resolutions(&to_resolve_imports); | ||
|
|
||
| self.indeterminate_imports = to_resolve_imports | ||
| .extract_if(.., |(_, _, count)| { |
There was a problem hiding this comment.
It would be nicer to extract_if into determined_imports instead and then do self.indeterminate_imports = imports_to_resolve;.
But it may be slower due to majority of the elements in the vector being determinate.
I'll benchmark it separately later after this PR lands.
|
|
||
| for (import, resolution) in import_resolutions { | ||
| let ImportResolution { imported_module, kind: resolution_kind } = resolution; | ||
| for (import, resolution, _) in import_resolutions { |
There was a problem hiding this comment.
| for (import, resolution, _) in import_resolutions { | |
| for &(import, resolution, _) in import_resolutions { |
Could you do something like this here to avoid *s below?
| type CmResolver<'r, 'ra, 'tcx> = ref_mut::RefOrMut<'r, Resolver<'ra, 'tcx>>; | ||
|
|
||
| // FIXME: this should be removed in the process of migration to parallel name resolution. | ||
| unsafe impl<'ra, 'tcx> DynSync for Resolver<'ra, 'tcx> {} |
There was a problem hiding this comment.
Could you remove the Dyn(Sync,Send) impls from this PR?
I don't think they are justified yet, before the migration to RwLock (and probably not yet used too).
Or maybe they are? At least for RefOrMut.
I'm not actually sure.
This is basically #158845 but we do not:
par_slicebecause:CmRefCellto useRwLocks(yet) because of perf reasons.The resolution loop is now in place instead of recollecting indeterminate imports.
Also implemented the unsafe traits
DynSend/DynSyncforRefOrMutandCmCelland tried to write correctSAFETYcomments.r? @petrochenkov