@@ -37,11 +37,12 @@ use stdarch_test::assert_instr;
3737/// The failure ordering must be [`Ordering::SeqCst`], [`Ordering::Acquire`] or
3838/// [`Ordering::Relaxed`], or this function call is undefined. See the `Atomic*`
3939/// documentation's `compare_exchange` function for more information. When
40- /// `compare_exchange` panics, this is undefined behavior. Currently this
41- /// function aborts the process with an undefined instruction.
40+ /// `compare_exchange` panics, this is undefined behavior.
4241#[ inline]
42+ #[ cfg_attr( miri, track_caller) ] // even without panics, this helps for Miri backtraces
4343#[ cfg_attr( test, assert_instr( cmpxchg16b, success = Ordering :: SeqCst , failure = Ordering :: SeqCst ) ) ]
4444#[ target_feature( enable = "cmpxchg16b" ) ]
45+ #[ stable( feature = "cmpxchg16b_instrinsic" , since = "1.67.0" ) ]
4546pub unsafe fn cmpxchg16b (
4647 dst : * mut u128 ,
4748 old : u128 ,
@@ -53,6 +54,8 @@ pub unsafe fn cmpxchg16b(
5354
5455 debug_assert ! ( dst as usize % 16 == 0 ) ;
5556
57+ // Copied from `atomic_compare_exchange` in `core`.
58+ // https://github.com/rust-lang/rust/blob/f8a2e49/library/core/src/sync/atomic.rs#L3046-L3079
5659 let ( val, _ok) = match ( success, failure) {
5760 ( Relaxed , Relaxed ) => intrinsics:: atomic_cxchg_relaxed_relaxed ( dst, old, new) ,
5861 ( Relaxed , Acquire ) => intrinsics:: atomic_cxchg_relaxed_acquire ( dst, old, new) ,
@@ -69,11 +72,12 @@ pub unsafe fn cmpxchg16b(
6972 ( SeqCst , Relaxed ) => intrinsics:: atomic_cxchg_seqcst_relaxed ( dst, old, new) ,
7073 ( SeqCst , Acquire ) => intrinsics:: atomic_cxchg_seqcst_acquire ( dst, old, new) ,
7174 ( SeqCst , SeqCst ) => intrinsics:: atomic_cxchg_seqcst_seqcst ( dst, old, new) ,
75+ ( _, AcqRel ) => panic ! ( "there is no such thing as an acquire-release failure ordering" ) ,
76+ ( _, Release ) => panic ! ( "there is no such thing as a release failure ordering" ) ,
7277
73- // The above block is all copied from libcore, and this statement is
74- // also copied from libcore except that it's a panic in libcore and we
75- // have a little bit more of a lightweight panic here.
76- _ => crate :: core_arch:: x86:: ud2 ( ) ,
78+ // `atomic::Ordering` is non_exhaustive. It warns when `core_arch` is built as a part of `core`.
79+ #[ allow( unreachable_patterns) ]
80+ ( _, _) => unreachable ! ( ) ,
7781 } ;
7882 val
7983}
0 commit comments