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

[SR-15785] TaskGroup addTask is blocking with poor performance #58062

Closed
jshier opened this issue Jan 29, 2022 · 5 comments
Closed

[SR-15785] TaskGroup addTask is blocking with poor performance #58062

jshier opened this issue Jan 29, 2022 · 5 comments
Assignees
Labels
bug A deviation from expected or documented behavior. Also: expected but undesirable behavior. concurrency Feature: umbrella label for concurrency language features performance standard library Area: Standard library umbrella swift 5.5

Comments

@jshier
Copy link
Contributor

jshier commented Jan 29, 2022

Previous ID SR-15785
Radar rdar://problem/88219931
Original Reporter @jshier
Type Bug
Status Resolved
Resolution Done
Environment

macOS 12.2, Xcode 13.2.1 and 13.3, 2020 i9 iMac, M1 Max MacBook Pro.

Additional Detail from JIRA
Votes 0
Component/s swift
Labels Bug, Concurrency, Performance
Assignee @Catfish-Man
Priority Medium

md5: cd628c72dea7e813640f5edee1597d34

Issue Description:

Attempting to enqueue many children, while quite easy with TaskGroup, is more than linear when you get into the tens of thousands. As a fundamental concurrency primitive, it would be beneficial if this performance could be improved.

Additionally, addTask seems to block the execution of children, letting memory balloon as the children are enqueued but aren't be executed.

Here's a simple example:

@main
struct ConcurrencyTest {
    static func main() async {
        let start = CFAbsoluteTimeGetCurrent()
        @Sendable
        func doNothing() {}
        
        await withTaskGroup(of: Void.self) { group in
            for _ in 0..<100_000 {
                group.addTask(operation: doNothing)
            }
            
            await group.waitForAll()
        }
        print(CFAbsoluteTimeGetCurrent() - start)
    }
}

This code takes 35.6s to execute on a 2020 i9 iMac and, shockingly, 89s on an M1 Max MacBook Pro.

@jshier
Copy link
Contributor Author

jshier commented Jan 29, 2022

Simply batching the execution allows 100_000 child tasks to complete in 0.125s on both Intel and M1.

@main
struct ConcurrencyTest {
    static func main() async {
        let start = CFAbsoluteTimeGetCurrent()
        await withTaskGroup(of: Void.self) { group in
            @Sendable
            func doNothing() {}

            var tasksToPerform = 99_990
            for _ in 0..<10 {
                group.addTask(operation: doNothing)
            }

            for await _ in group {
                if tasksToPerform > 0 {
                    group.addTask(operation: doNothing)
                    tasksToPerform -= 1
                }
            }
        }
        print(CFAbsoluteTimeGetCurrent() - start)
    }
}

@weissi
Copy link
Member

weissi commented Jan 29, 2022

Thanks for filing this! I had seen this too pre-release (can't find the radar now...) and hoped this was fixed 🙁.

@weissi
Copy link
Member

weissi commented Jan 29, 2022

@swift-ci create

@weissi
Copy link
Member

weissi commented Jan 29, 2022

CC @rjmccall/@ktoso

@ktoso
Copy link
Member

ktoso commented Feb 3, 2022

We looked into this with David and Rokhini, PR here: #41165

@swift-ci swift-ci transferred this issue from apple/swift-issues Apr 25, 2022
@AnthonyLatsis AnthonyLatsis added runtime The Swift Runtime standard library Area: Standard library umbrella swift 5.5 and removed swift runtime The Swift Runtime labels Jan 16, 2023
This issue was closed.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug A deviation from expected or documented behavior. Also: expected but undesirable behavior. concurrency Feature: umbrella label for concurrency language features performance standard library Area: Standard library umbrella swift 5.5
Projects
None yet
Development

No branches or pull requests

4 participants