@@ -10761,7 +10761,7 @@ the same memory. Concurrent programming is tricky for many reasons, most
10761
10761
importantly that it is undefined behavior to read data in one thread after it
10762
10762
was written by another thread, if there is no proper synchronization between
10763
10763
those threads. Making existing single-threaded code execute concurrently can be
10764
- as trivial as adding `std::async` or `std::thread` strategically, or it can be
10764
+ as trivial as adding `std::async` or `std::thread` strategically, or it can
10765
10765
necessitate a full rewrite, depending on whether the original code was written
10766
10766
in a thread-friendly way.
10767
10767
@@ -10940,7 +10940,7 @@ Help the tools:
10940
10940
##### Reason
10941
10941
10942
10942
If you don't share writable data, you can't have a data race.
10943
- The less sharing you do, the less chance you have to forget to synchanize access (and get data races).
10943
+ The less sharing you do, the less chance you have to forget to synchronize access (and get data races).
10944
10944
The less sharing you do, the less chance you have to wait on a lock (so performance can improve).
10945
10945
10946
10946
##### Example
@@ -10966,7 +10966,7 @@ The less sharing you do, the less chance you have to wait on a lock (so performa
10966
10966
// ...
10967
10967
}
10968
10968
10969
- Without those `const`s, we would have to review every asynchroneously invoked function for potential data races on `surface_readings`.
10969
+ Without those `const`s, we would have to review every asynchronously invoked function for potential data races on `surface_readings`.
10970
10970
10971
10971
##### Note
10972
10972
@@ -10982,7 +10982,7 @@ No locking is needed: You can't have a data race on a constant.
10982
10982
10983
10983
##### Reason
10984
10984
10985
- A `thread` is a implementation concept, a way of thinking about the machine.
10985
+ A `thread` is an implementation concept, a way of thinking about the machine.
10986
10986
A task is an application notion, something you'd like to do, preferably concurrently with other tasks.
10987
10987
Application concepts are easier to reason about.
10988
10988
@@ -11073,7 +11073,7 @@ Concurrency rule summary:
11073
11073
* [CP.27: Use plain `std::thread` for `thread`s that detach based on a run-time condition (only)](#Rconc-thread)
11074
11074
* [CP.28: Remember to join scoped `thread`s that are not `detach()`ed](#Rconc-join)
11075
11075
* [CP.30: Do not pass pointers to local variables to non-`raii_thread's](#Rconc-pass)
11076
- * [CP.31: Pass small amounts of data between threads by value, reather by reference or pointer](#Rconc-data)
11076
+ * [CP.31: Pass small amounts of data between threads by value, rather than by reference or pointer](#Rconc-data)
11077
11077
* [CP.32: To share ownership beween unrelated `thread`s use `shared_ptr`](#Rconc-shared)
11078
11078
* [CP.40: Minimize context switching](#Rconc-switch)
11079
11079
* [CP.41: Minimize thread creation and destruction](#Rconc-create)
@@ -11216,7 +11216,7 @@ If, as it is likely, `f()` invokes operations on `*this`, we must make sure that
11216
11216
11217
11217
##### Reason
11218
11218
11219
- To maintain pointer safety and avoid leaks, we need to consider what pointers a used by a `thread`.
11219
+ To maintain pointer safety and avoid leaks, we need to consider what pointers are used by a `thread`.
11220
11220
If a `thread` joins, we can safely pass pointers to objects in the scope of the `thread` and its enclosing scopes.
11221
11221
11222
11222
##### Example
@@ -11255,7 +11255,7 @@ After that, the usual lifetime and ownership (for local objects) enforcement app
11255
11255
11256
11256
##### Reason
11257
11257
11258
- To maintain pointer safety and avoid leaks, we need to consider what pointers a used by a `thread`.
11258
+ To maintain pointer safety and avoid leaks, we need to consider what pointers are used by a `thread`.
11259
11259
If a `thread` is detached, we can safely pass pointers to static and free store objects (only).
11260
11260
11261
11261
##### Example
@@ -11415,7 +11415,7 @@ A `thread` that has not been `detach()`ed when it is destroyed terminates the pr
11415
11415
11416
11416
##### Reason
11417
11417
11418
- In general, you cannot know whether a non-`raii_thread` will outlife your thread ( so that those pointers will become invalid.
11418
+ In general, you cannot know whether a non-`raii_thread` will outlive the scope of the variables, so that those pointers will become invalid.
11419
11419
11420
11420
##### Example, bad
11421
11421
@@ -11427,7 +11427,7 @@ In general, you cannot know whether a non-`raii_thread` will outlife your thread
11427
11427
t0.detach();
11428
11428
}
11429
11429
11430
- The detach` may not be so easy to spot.
11430
+ The ` detach` may not be so easy to spot.
11431
11431
Use a `raii_thread` or don't pass the pointer.
11432
11432
11433
11433
##### Example, bad
@@ -11436,10 +11436,10 @@ Use a `raii_thread` or don't pass the pointer.
11436
11436
11437
11437
##### Enforcement
11438
11438
11439
- Flage pointers to locals passed in the constructor of a plain `thread`.
11439
+ Flag pointers to locals passed in the constructor of a plain `thread`.
11440
11440
11441
11441
11442
- ### <a name="Rconc-switch"></a>CP.31: Pass small amounts of data between threads by value, reather by reference or pointer
11442
+ ### <a name="Rconc-switch"></a>CP.31: Pass small amounts of data between threads by value, rather by reference or pointer
11443
11443
11444
11444
##### Reason
11445
11445
@@ -11448,7 +11448,7 @@ Copying naturally gives unique ownership (simplifies code) and eliminates the po
11448
11448
11449
11449
##### Note
11450
11450
11451
- Defining "small amount" precisely and is impossible.
11451
+ Defining "small amount" precisely is impossible.
11452
11452
11453
11453
##### Example
11454
11454
@@ -11463,7 +11463,7 @@ Defining "small amount" precisely and is impossible.
11463
11463
11464
11464
The call of `modify1` involves copying two `string` values; the call of `modify2` does not.
11465
11465
On the other hand, the implementation of `modify1` is exactly as we would have written in for single-threaded code,
11466
- wheread the implementation of `modify2` will need some form of locking to avoid data races.
11466
+ whereas the implementation of `modify2` will need some form of locking to avoid data races.
11467
11467
If the string is short (say 10 characters), the call of `modify1` can be surprisingly fast;
11468
11468
essentially all the cost is in the `thread` switch. If the string is long (say 1,000,000 characters), copying it twice
11469
11469
is probably not a good idea.
@@ -11480,7 +11480,7 @@ message passing or shared memory.
11480
11480
11481
11481
##### Reason
11482
11482
11483
- If treads are unrelated (that is, not known to be in the same scope or one within the lifetime of the other)
11483
+ If threads are unrelated (that is, not known to be in the same scope or one within the lifetime of the other)
11484
11484
and they need to share free store memory that needs to be deleted, a `shared_ptr` (or equivalent) is the only
11485
11485
safe way to ensure proper deletion.
11486
11486
@@ -11490,7 +11490,7 @@ safe way to ensure proper deletion.
11490
11490
11491
11491
##### Note
11492
11492
11493
- * A static object (e.g. a global) can be shard because it is not owned in the sense that some thread is responsible for it's deletion.
11493
+ * A static object (e.g. a global) can be shared because it is not owned in the sense that some thread is responsible for it's deletion.
11494
11494
* An object on free store that is never to be deleted can be shared.
11495
11495
* An object owned by one thread can be safely shared with another as long as that second thread doesn't outlive the owner.
11496
11496
@@ -11503,7 +11503,7 @@ safe way to ensure proper deletion.
11503
11503
11504
11504
##### Reason
11505
11505
11506
- Context swtiches are expesive .
11506
+ Context swtiches are expensive .
11507
11507
11508
11508
##### Example
11509
11509
@@ -11562,7 +11562,7 @@ Instead, we could have a set of pre-created worker threads processing the messag
11562
11562
11563
11563
##### Note
11564
11564
11565
- If you system has a good thread pool, use it.
11565
+ If your system has a good thread pool, use it.
11566
11566
If your system has a good message queue, use it.
11567
11567
11568
11568
##### Enforcement
@@ -11637,7 +11637,7 @@ it will immediately go back to sleep, waiting.
11637
11637
11638
11638
##### Enforcement
11639
11639
11640
- Flag all `waits` without conditions.
11640
+ Flag all `wait`s without conditions.
11641
11641
11642
11642
11643
11643
### <a name="Rconc-time"></a>CP.43: Minimize time spent in a critical section
0 commit comments