11// Copyright 2023-Present Datadog, Inc. https://www.datadoghq.com/
22// SPDX-License-Identifier: Apache-2.0
33
4- use std:: sync:: atomic:: { AtomicI64 , Ordering :: SeqCst } ;
4+ use std:: sync:: atomic:: { AtomicI64 , Ordering } ;
55use thiserror:: Error ;
66
77#[ cfg( unix) ]
@@ -48,7 +48,6 @@ impl OpTypes {
4848#[ allow( clippy:: declare_interior_mutable_const) ]
4949const ATOMIC_ZERO : AtomicI64 = AtomicI64 :: new ( 0 ) ;
5050
51- // TODO: Is this
5251static OP_COUNTERS : [ AtomicI64 ; OpTypes :: SIZE as usize ] = [ ATOMIC_ZERO ; OpTypes :: SIZE as usize ] ;
5352
5453/// Track that an operation (of type op) has begun.
@@ -58,9 +57,7 @@ static OP_COUNTERS: [AtomicI64; OpTypes::SIZE as usize] = [ATOMIC_ZERO; OpTypes:
5857/// ATOMICITY:
5958/// This function is atomic.
6059pub fn begin_op ( op : OpTypes ) -> Result < ( ) , CounterError > {
61- // TODO: I'm making everything SeqCst for now. Could possibly gain some
62- // performance by using a weaker ordering.
63- let old = OP_COUNTERS [ op as usize ] . fetch_add ( 1 , SeqCst ) ;
60+ let old = OP_COUNTERS [ op as usize ] . fetch_add ( 1 , Ordering :: Relaxed ) ;
6461 if old == i64:: MAX - 1 {
6562 return Err ( CounterError :: CounterOverflow ( op) ) ;
6663 }
@@ -72,7 +69,7 @@ pub fn begin_op(op: OpTypes) -> Result<(), CounterError> {
7269/// PRECONDITIONS: This function assumes that the crash-tracker is initialized.
7370/// ATOMICITY: This function is atomic.
7471pub fn end_op ( op : OpTypes ) -> Result < ( ) , CounterError > {
75- let old = OP_COUNTERS [ op as usize ] . fetch_sub ( 1 , SeqCst ) ;
72+ let old = OP_COUNTERS [ op as usize ] . fetch_sub ( 1 , Ordering :: Relaxed ) ;
7673 if old <= 0 {
7774 return Err ( CounterError :: OperationNotStarted ( op) ) ;
7875 }
@@ -103,7 +100,12 @@ pub fn emit_counters(w: &mut impl Write) -> Result<(), CounterError> {
103100
104101 writeln ! ( w, "{DD_CRASHTRACK_BEGIN_COUNTERS}" ) ?;
105102 for ( i, c) in OP_COUNTERS . iter ( ) . enumerate ( ) {
106- writeln ! ( w, "{{\" {}\" : {}}}" , OpTypes :: name( i) ?, c. load( SeqCst ) ) ?;
103+ writeln ! (
104+ w,
105+ "{{\" {}\" : {}}}" ,
106+ OpTypes :: name( i) ?,
107+ c. load( Ordering :: Relaxed )
108+ ) ?;
107109 }
108110 writeln ! ( w, "{DD_CRASHTRACK_END_COUNTERS}" ) ?;
109111 w. flush ( ) ?;
@@ -113,12 +115,12 @@ pub fn emit_counters(w: &mut impl Write) -> Result<(), CounterError> {
113115/// Resets all counters to 0.
114116/// Expected to be used after a fork, to reset the counters on the child
115117/// ATOMICITY:
116- /// This is NOT ATOMIC .
118+ /// The reset of each individual counter is atomic, but the entire reset is NOT .
117119/// Should only be used when no conflicting updates can occur,
118120/// e.g. after a fork but before ops start on the child.
119121pub fn reset_counters ( ) -> Result < ( ) , CounterError > {
120122 for c in OP_COUNTERS . iter ( ) {
121- c. store ( 0 , SeqCst ) ;
123+ c. store ( 0 , Ordering :: Relaxed ) ;
122124 }
123125 Ok ( ( ) )
124126}
0 commit comments