@@ -573,7 +573,7 @@ impl<T> From<T> for RwLock<T> {
573573}
574574
575575impl < ' rwlock , T : ?Sized > RwLockReadGuard < ' rwlock , T > {
576- /// Create a new instance of `RwLockReadGuard<T>` from a `RwLock<T>`.
576+ /// Creates a new instance of `RwLockReadGuard<T>` from a `RwLock<T>`.
577577 ///
578578 /// # Safety
579579 ///
@@ -964,9 +964,51 @@ impl<'a, T: ?Sized> RwLockWriteGuard<'a, T> {
964964
965965 /// Downgrades a write-locked `RwLockWriteGuard` into a read-locked [`RwLockReadGuard`].
966966 ///
967- /// Atomically changes the state of the [`RwLock`] from exclusive mode into shared mode.
967+ /// This method will atomically change the state of the [`RwLock`] from exclusive mode into
968+ /// shared mode. This means that it is impossible for a writing thread to get in between a
969+ /// thread calling `downgrade` and the same thread reading whatever it wrote while it had the
970+ /// [`RwLock`] in write mode.
968971 ///
969- /// FIXME MORE DOCS COMING SOON.
972+ /// Note that since we have the `RwLockWriteGuard`, we know that the [`RwLock`] is already
973+ /// locked for writing, so this method cannot fail.
974+ ///
975+ /// # Example
976+ ///
977+ /// ```
978+ /// #![feature(rwlock_downgrade)]
979+ /// use std::sync::{Arc, RwLock, RwLockWriteGuard};
980+ ///
981+ /// // The inner value starts as 0.
982+ /// let rw = Arc::new(RwLock::new(0));
983+ ///
984+ /// // Put the lock in write mode.
985+ /// let mut main_write_guard = rw.write().unwrap();
986+ ///
987+ /// let evil = rw.clone();
988+ /// let handle = std::thread::spawn(move || {
989+ /// // This will not return until the main thread drops the `main_read_guard`.
990+ /// let mut evil_guard = evil.write().unwrap();
991+ ///
992+ /// assert_eq!(*evil_guard, 1);
993+ /// *evil_guard = 2;
994+ /// });
995+ ///
996+ /// // After spawning the writer thread, set the inner value to 1.
997+ /// *main_write_guard = 1;
998+ ///
999+ /// // Atomically downgrade the write guard into a read guard.
1000+ /// let main_read_guard = RwLockWriteGuard::downgrade(main_write_guard);
1001+ ///
1002+ /// // Since `downgrade` is atomic, the writer thread cannot have set the inner value to 2.
1003+ /// assert_eq!(*main_read_guard, 1, "`downgrade` was not atomic");
1004+ ///
1005+ /// // Clean up everything now
1006+ /// drop(main_read_guard);
1007+ /// handle.join().unwrap();
1008+ ///
1009+ /// let final_check = rw.read().unwrap();
1010+ /// assert_eq!(*final_check, 2);
1011+ /// ```
9701012 #[ unstable( feature = "rwlock_downgrade" , issue = "128203" ) ]
9711013 pub fn downgrade ( s : Self ) -> RwLockReadGuard < ' a , T > {
9721014 let lock = s. lock ;
0 commit comments