Skip to content

Commit

Permalink
wip
Browse files Browse the repository at this point in the history
  • Loading branch information
mgeisler committed Oct 15, 2024
1 parent c4958b6 commit 9d5daf8
Show file tree
Hide file tree
Showing 10 changed files with 24 additions and 26 deletions.
4 changes: 4 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ members = [
"src/borrowing",
"src/control-flow-basics",
"src/error-handling",
"src/concurrency",
"src/concurrency/sync-exercises",
"src/concurrency/async-exercises",
"src/concurrency/async-exercises/chat-async",
Expand Down
2 changes: 1 addition & 1 deletion src/SUMMARY.md
Original file line number Diff line number Diff line change
Expand Up @@ -387,7 +387,7 @@
- [Futures](concurrency/async/futures.md)
- [Runtimes](concurrency/async/runtimes.md)
- [Tokio](concurrency/async/runtimes/tokio.md)
- [Tasks](concurrency/async/tasks.md)
<!-- - [Tasks](concurrency/async/tasks.md) -->
- [Channels and Control Flow](concurrency/async-control-flow.md)
- [Async Channels](concurrency/async-control-flow/channels.md)
- [Join](concurrency/async-control-flow/join.md)
Expand Down
2 changes: 1 addition & 1 deletion src/concurrency/async-control-flow/channels.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ minutes: 8

# Async Channels

Several crates have support for asynchronous channels. For instance `tokio`:
Asynchronous channels are very similar to synchronous channels:

```rust,editable,compile_fail
{{#include channels.rs}}
Expand Down
2 changes: 0 additions & 2 deletions src/concurrency/async-control-flow/channels.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,10 @@ use tokio::sync::mpsc;

async fn ping_handler(mut input: mpsc::Receiver<()>) {
let mut count = 0;

while let Some(_) = input.recv().await {
count += 1;
println!("Received {count} pings so far.");
}

println!("ping_handler complete");
}

Expand Down
13 changes: 6 additions & 7 deletions src/concurrency/async-exercises/chat-app.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,13 +29,13 @@ You are going to need the following functions from `tokio` and
[`tokio_websockets`][2]. Spend a few minutes to familiarize yourself with the
API.

- [StreamExt::next()][3] implemented by `WebSocketStream`: for asynchronously
- [`StreamExt::next()`][3] implemented by `WebSocketStream`: for asynchronously
reading messages from a Websocket Stream.
- [SinkExt::send()][4] implemented by `WebSocketStream`: for asynchronously
- [`SinkExt::send()`][4] implemented by `WebSocketStream`: for asynchronously
sending messages on a Websocket Stream.
- [Lines::next_line()][5]: for asynchronously reading user messages from the
- [`Lines::next_line()`][5]: for asynchronously reading user messages from the
standard input.
- [Sender::subscribe()][6]: for subscribing to a broadcast channel.
- [`Sender::subscribe()`][6]: for subscribing to a broadcast channel.

## Two binaries

Expand All @@ -58,9 +58,8 @@ _src/bin/server.rs_:
{{#include chat-async/src/bin/server.rs:setup}}
{{#include chat-async/src/bin/server.rs:handle_connection}}
// TODO: For a hint, see the description of the task below.
Ok(())
{{#include chat-async/src/bin/server.rs:main}}
```

Expand All @@ -72,7 +71,7 @@ _src/bin/client.rs_:
{{#include chat-async/src/bin/client.rs:setup}}
// TODO: For a hint, see the description of the task below.
Ok(())
}
```

Expand Down
4 changes: 1 addition & 3 deletions src/concurrency/async-exercises/dining-philosophers.rs
Original file line number Diff line number Diff line change
Expand Up @@ -44,13 +44,11 @@ impl Philosopher {
// Keep trying until we have both forks
// ANCHOR_END: Philosopher-eat
let (_left_fork, _right_fork) = loop {
tokio::task::yield_now().await;
// Pick up forks...
match (self.left_fork.try_lock(), self.right_fork.try_lock()) {
(Ok(left_fork), Ok(right_fork)) => (left_fork, right_fork),
(Ok(left_fork), Ok(right_fork)) => break (left_fork, right_fork),
(_, _) => continue,
};
break (left_fork, right_fork);
};

// ANCHOR: Philosopher-eat-body
Expand Down
6 changes: 3 additions & 3 deletions src/concurrency/async-pitfalls/async-traits.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,9 @@ minutes: 5

# Async Traits

Async methods in traits are were stabilized in the 1.75 release. This required
support for using return-position `impl Trait` in traits, as the desugaring for
`async fn` includes `-> impl Future<Output = ...>`.
Async methods in traits are were stabilized in the 1.75 release (December 2023).
This required support for using return-position `impl Trait` in traits, as the
desugaring for `async fn` includes `-> impl Future<Output = ...>`.

However, even with the native support, there are some pitfalls around
`async fn`:
Expand Down
12 changes: 4 additions & 8 deletions src/concurrency/async-pitfalls/async-traits.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
use async_trait::async_trait;
use std::time::Instant;
use tokio::time::{sleep, Duration};

#[async_trait]
Expand All @@ -18,14 +17,11 @@ impl Sleeper for FixedSleeper {
}
}

async fn run_all_sleepers_multiple_times(
sleepers: Vec<Box<dyn Sleeper>>,
n_times: usize,
) {
for _ in 0..n_times {
async fn run_all_sleepers_multiple_times(sleepers: Vec<Box<dyn Sleeper>>) {
for _ in 0..5 {
println!("Running all sleepers...");
for sleeper in &sleepers {
let start = Instant::now();
let start = std::time::Instant::now();
sleeper.sleep().await;
println!("Slept for {} ms", start.elapsed().as_millis());
}
Expand All @@ -38,5 +34,5 @@ async fn main() {
Box::new(FixedSleeper { sleep_ms: 50 }),
Box::new(FixedSleeper { sleep_ms: 100 }),
];
run_all_sleepers_multiple_times(sleepers, 5).await;
run_all_sleepers_multiple_times(sleepers).await;
}
4 changes: 3 additions & 1 deletion src/concurrency/async-pitfalls/pin.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,11 @@ minutes: 20
# `Pin`

Async blocks and functions return types implementing the `Future` trait. The
type returned is the result of a compiler transformation which turns local
type returned is the result of a [compiler transformation] which turns local
variables into data stored inside the future.

[compiler transformation]: https://tokio.rs/tokio/tutorial/async

Some of those variables can hold pointers to other local variables. Because of
that, the future should never be moved to a different memory location, as it
would invalidate those pointers.
Expand Down

0 comments on commit 9d5daf8

Please sign in to comment.