Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Make SyncDroplessArena allocations thread-local in the fast path #61873

Closed
wants to merge 2 commits into from

Conversation

Zoxc
Copy link
Contributor

@Zoxc Zoxc commented Jun 15, 2019

This works by having a thread local chunk to allocate from and a global list of chunks for in_arena to use.

r? @eddyb

@rust-highfive rust-highfive added the S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. label Jun 15, 2019
@rust-highfive
Copy link
Collaborator

The job x86_64-gnu-llvm-6.0 of your PR failed on Travis (raw log). Through arcane magic we have determined that the following fragments from the build log may contain information about the problem.

Click to expand the log.
travis_time:end:138e0ab4:start=1560636922330806312,finish=1560636924688547365,duration=2357741053
$ git checkout -qf FETCH_HEAD
travis_fold:end:git.checkout

Encrypted environment variables have been removed for security reasons.
See https://docs.travis-ci.com/user/pull-requests/#pull-requests-and-security-restrictions
$ export SCCACHE_BUCKET=rust-lang-ci-sccache2
$ export SCCACHE_REGION=us-west-1
$ export GCP_CACHE_BUCKET=rust-lang-ci-cache
$ export AWS_ACCESS_KEY_ID=AKIA46X5W6CZEJZ6XT55
---
[00:07:20]    Compiling rustc_data_structures v0.0.0 (/checkout/src/librustc_data_structures)
[00:07:22] error[E0308]: mismatched types
[00:07:22]    --> src/librustc_data_structures/sync.rs:229:35
[00:07:22]     |
[00:07:22] 229 |                 SharedWorkerLocal(OneThread::new(f(0)))
[00:07:22]     |                                   ^^^^^^^^^^^^^^^^^^^^ expected type parameter, found struct `sync::OneThread`
[00:07:22]     = note: expected type `T`
[00:07:22]     = note: expected type `T`
[00:07:22]                found type `sync::OneThread<T>`
[00:07:23] error: aborting due to previous error
[00:07:23] 
[00:07:23] For more information about this error, try `rustc --explain E0308`.
[00:07:23] error: Could not compile `rustc_data_structures`.
---
travis_time:end:0301eff5:start=1560637392091412071,finish=1560637392096760232,duration=5348161
travis_fold:end:after_failure.3
travis_fold:start:after_failure.4
travis_time:start:03a6275a
$ ln -s . checkout && for CORE in obj/cores/core.*; do EXE=$(echo $CORE | sed 's|obj/cores/core\.[0-9]*\.!checkout!\(.*\)|\1|;y|!|/|'); if [ -f "$EXE" ]; then printf travis_fold":start:crashlog\n\033[31;1m%s\033[0m\n" "$CORE"; gdb --batch -q -c "$CORE" "$EXE" -iex 'set auto-load off' -iex 'dir src/' -iex 'set sysroot .' -ex bt -ex q; echo travis_fold":"end:crashlog; fi; done || true
travis_fold:end:after_failure.4
travis_fold:start:after_failure.5
travis_time:start:2f9866ec
travis_time:start:2f9866ec
$ cat ./obj/build/x86_64-unknown-linux-gnu/native/asan/build/lib/asan/clang_rt.asan-dynamic-i386.vers || true
cat: ./obj/build/x86_64-unknown-linux-gnu/native/asan/build/lib/asan/clang_rt.asan-dynamic-i386.vers: No such file or directory
travis_fold:end:after_failure.5
travis_fold:start:after_failure.6
travis_time:start:014422e0
$ dmesg | grep -i kill

I'm a bot! I can only do what humans tell me to, so if this was not helpful or you have suggestions for improvements, please ping or otherwise contact @TimNN. (Feature Requests)

@eddyb
Copy link
Member

eddyb commented Jun 16, 2019

I don't know how any of this concurrent code works, sorry! (Or rather, why it might be safe)
Maybe if @aturon gets back, he can help with reviewing it?

cc @rust-lang/compiler Is anyone else comfortable with concurrent data structures and willing to review?

@nikomatsakis nikomatsakis assigned nikomatsakis and aturon and unassigned eddyb Jun 18, 2019
@nikomatsakis
Copy link
Contributor

I'll review it and/or get @aturon to do so =)

@Dylan-DPC-zz
Copy link

ping from triage @nikomatsakis @aturon any updates on this?

@aturon
Copy link
Member

aturon commented Jul 8, 2019

Hey @Dylan-DPC, I plan to review this one, however at the moment I'm getting up to speed on the concurrency approach in general.

@Dylan-DPC-zz
Copy link

thanks. No issues.

@eddyb
Copy link
Member

eddyb commented Jul 11, 2019

Also pinging @gankro and @stjepang, in case they want to review as well.

@Gankra
Copy link
Contributor

Gankra commented Jul 11, 2019

I do not

@hdhoang
Copy link
Contributor

hdhoang commented Jul 26, 2019

ping from triage @stjepang, could you provide comment on this PR?

@hdhoang hdhoang added S-waiting-on-team Status: Awaiting decision from the relevant subteam (see the T-<team> label). T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Jul 26, 2019
@nagisa nagisa added S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. and removed S-waiting-on-team Status: Awaiting decision from the relevant subteam (see the T-<team> label). labels Aug 8, 2019
pub fn clear(&mut self) {
self.lock.get_mut().clear();
fn grow(&self, n: usize, chunks: &mut Vec<TypedArenaChunk<T>>) {
unsafe {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would be great if these large unsafe { .. } blocks would have comments justifying their soundness.
(Applies throughout the PR.)

@wirelessringo
Copy link

Ping from triage. @aturon any updates on this? Thanks

@JohnCSimon
Copy link
Member

Pinging again from triage
This PR has sat idle waiting for review for eight days.
@Centril @aturon

Thanks.

@Dylan-DPC-zz
Copy link

Waiting for a review from @rust-lang/compilers

impl<T> CurrentChunk<T> {
#[inline]
fn align(&self, align: usize) {
let final_address = ((self.ptr.get() as usize) + align - 1) & !(align - 1);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

self.lock.get_mut().clear();
fn grow(&self, n: usize, chunks: &mut Vec<TypedArenaChunk<T>>) {
unsafe {
let (chunk, mut new_capacity);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

move chunk declaration to initialization site

fn grow(&self, n: usize, chunks: &mut Vec<TypedArenaChunk<T>>) {
unsafe {
let (chunk, mut new_capacity);
if let Some(last_chunk) = chunks.last_mut() {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The statements in the Some block of this if let deserve some documenting comments.


current.align(align);

let future_end = intrinsics::arith_offset(current.ptr.get(), bytes as isize);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why not use https://doc.rust-lang.org/std/primitive.pointer.html#method.wrapping_offset here? Intrinsics should not be used except in their wrapper code

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Alternatively you can use offset_from to compute the offset between end and ptr and see if that is bigger than bytes. I think I'd prefer it that way around.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh, we stabilized this intrinsic? That seems unfortunate as it can be used to create invalid pointers (which are UB in C).

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's not stable. and it's still unsafe, so if you think there are problems with it, please raise them on the tracking issue (#41079). wrapping_offset_from is safe.

let ptr = current.ptr.get();
// Set the pointer past ourselves
current.ptr.set(
intrinsics::arith_offset(current.ptr.get(), bytes as isize) as *mut u8,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

since we just grew the thing, we can now use ptr::offset, right?

@oli-obk oli-obk assigned oli-obk and unassigned aturon Aug 26, 2019
@JohnCSimon
Copy link
Member

Ping from triage -
@Zoxc @oli-obk @rust-lang/compilers
This has sat idle for two weeks. What needs to happen for this pr?

Thanks

@oli-obk oli-obk added S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. and removed S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. labels Sep 8, 2019
@joelpalmer
Copy link

Ping from Triage: closing due to inactivity. Please re-open if there are updates. @Zoxc

@joelpalmer joelpalmer closed this Sep 16, 2019
@joelpalmer joelpalmer added S-inactive Status: Inactive and waiting on the author. This is often applied to closed PRs. and removed S-waiting-on-author Status: This is awaiting some action (such as code changes or more information) from the author. labels Sep 16, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
S-inactive Status: Inactive and waiting on the author. This is often applied to closed PRs. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.
Projects
None yet
Development

Successfully merging this pull request may close these issues.