]> git.saurik.com Git - apple/libdispatch.git/blobdiff - src/trace.h
libdispatch-913.30.4.tar.gz
[apple/libdispatch.git] / src / trace.h
index ebab27c888203f2311950571c59bbd3f40882058..c670f60b7944e1ee4593b29a4203d0f45c6a632b 100644 (file)
 #ifndef __DISPATCH_TRACE__
 #define __DISPATCH_TRACE__
 
-#if !__OBJC2__ && !defined(__cplusplus)
-
-#if DISPATCH_USE_DTRACE || DISPATCH_USE_DTRACE_INTROSPECTION
-typedef struct dispatch_trace_timer_params_s {
-       int64_t deadline, interval, leeway;
-} *dispatch_trace_timer_params_t;
-
-#include "provider.h"
-#endif // DISPATCH_USE_DTRACE || DISPATCH_USE_DTRACE_INTROSPECTION
+#if DISPATCH_PURE_C
 
 #if DISPATCH_USE_DTRACE_INTROSPECTION
 #define _dispatch_trace_callout(_c, _f, _dcc) do { \
@@ -92,12 +84,13 @@ _dispatch_trace_client_callout2(void *ctxt, size_t i, void (*f)(void *, size_t))
                char *_kind; \
                dispatch_function_t _func; \
                void *_ctxt; \
-               if (DISPATCH_OBJ_IS_VTABLE(_do)) { \
+               if (_dispatch_object_has_vtable(_do)) { \
                        _kind = (char*)dx_kind(_do); \
                        if ((dx_type(_do) & _DISPATCH_META_TYPE_MASK) == \
                                        _DISPATCH_SOURCE_TYPE && (_dq) != &_dispatch_mgr_q) { \
                                dispatch_source_t _ds = (dispatch_source_t)_do; \
-                               _dc = _ds->ds_refs->ds_handler[DS_EVENT_HANDLER]; \
+                               _dc = os_atomic_load(&_ds->ds_refs->ds_handler[ \
+                                               DS_EVENT_HANDLER], relaxed); \
                                _func = _dc ? _dc->dc_func : NULL; \
                                _ctxt = _dc ? _dc->dc_ctxt : NULL; \
                        } else { \
@@ -107,10 +100,10 @@ _dispatch_trace_client_callout2(void *ctxt, size_t i, void (*f)(void *, size_t))
                } else { \
                        _dc = (void*)_do; \
                        _ctxt = _dc->dc_ctxt; \
-                       if ((long)_dc->do_vtable & DISPATCH_OBJ_SYNC_SLOW_BIT) { \
+                       if (_dc->dc_flags & DISPATCH_OBJ_SYNC_WAITER_BIT) { \
                                _kind = "semaphore"; \
                                _func = (dispatch_function_t)dispatch_semaphore_signal; \
-                       } else if (_dc->dc_func == _dispatch_call_block_and_release) { \
+                       } else if (_dc->dc_flags & DISPATCH_OBJ_BLOCK_BIT) { \
                                _kind = "block"; \
                                _func = _dispatch_Block_invoke(_dc->dc_ctxt); \
                        } else { \
@@ -130,8 +123,8 @@ _dispatch_trace_client_callout2(void *ctxt, size_t i, void (*f)(void *, size_t))
 #if DISPATCH_USE_DTRACE_INTROSPECTION || DISPATCH_INTROSPECTION
 DISPATCH_ALWAYS_INLINE
 static inline void
-_dispatch_trace_queue_push_list(dispatch_queue_t dq, dispatch_object_t _head,
-               dispatch_object_t _tail, pthread_priority_t pp, unsigned int n)
+_dispatch_trace_root_queue_push_list(dispatch_queue_t dq,
+               dispatch_object_t _head, dispatch_object_t _tail, int n)
 {
        if (slowpath(DISPATCH_QUEUE_PUSH_ENABLED())) {
                struct dispatch_object_s *dou = _head._do;
@@ -140,32 +133,20 @@ _dispatch_trace_queue_push_list(dispatch_queue_t dq, dispatch_object_t _head,
                } while (dou != _tail._do && (dou = dou->do_next));
        }
        _dispatch_introspection_queue_push_list(dq, _head, _tail);
-       _dispatch_queue_push_list(dq, _head, _tail, pp, n);
-}
-
-DISPATCH_ALWAYS_INLINE
-static inline void
-_dispatch_trace_queue_push(dispatch_queue_t dq, dispatch_object_t _tail, pthread_priority_t pp)
-{
-       if (slowpath(DISPATCH_QUEUE_PUSH_ENABLED())) {
-               struct dispatch_object_s *dou = _tail._do;
-               _dispatch_trace_continuation(dq, dou, DISPATCH_QUEUE_PUSH);
-       }
-       _dispatch_introspection_queue_push(dq, _tail);
-       _dispatch_queue_push(dq, _tail, pp);
+       _dispatch_root_queue_push_inline(dq, _head, _tail, n);
 }
 
 DISPATCH_ALWAYS_INLINE
 static inline void
-_dispatch_trace_queue_push_wakeup(dispatch_queue_t dq, dispatch_object_t _tail,
-               pthread_priority_t pp, bool wakeup)
+_dispatch_trace_queue_push_inline(dispatch_queue_t dq, dispatch_object_t _tail,
+               dispatch_qos_t qos)
 {
        if (slowpath(DISPATCH_QUEUE_PUSH_ENABLED())) {
                struct dispatch_object_s *dou = _tail._do;
                _dispatch_trace_continuation(dq, dou, DISPATCH_QUEUE_PUSH);
        }
        _dispatch_introspection_queue_push(dq, _tail);
-       _dispatch_queue_push_wakeup(dq, _tail, pp, wakeup);
+       _dispatch_queue_push_inline(dq, _tail, qos);
 }
 
 DISPATCH_ALWAYS_INLINE
@@ -179,16 +160,8 @@ _dispatch_trace_continuation_push(dispatch_queue_t dq, dispatch_object_t _tail)
        _dispatch_introspection_queue_push(dq, _tail);
 }
 
-DISPATCH_ALWAYS_INLINE
-static inline void
-_dispatch_queue_push_notrace(dispatch_queue_t dq, dispatch_object_t dou, pthread_priority_t pp)
-{
-       _dispatch_queue_push(dq, dou, pp);
-}
-
-#define _dispatch_queue_push_list _dispatch_trace_queue_push_list
-#define _dispatch_queue_push _dispatch_trace_queue_push
-#define _dispatch_queue_push_wakeup _dispatch_trace_queue_push_wakeup
+#define _dispatch_root_queue_push_inline _dispatch_trace_root_queue_push_list
+#define _dispatch_queue_push_inline _dispatch_trace_queue_push_inline
 
 DISPATCH_ALWAYS_INLINE
 static inline void
@@ -200,7 +173,6 @@ _dispatch_trace_continuation_pop(dispatch_queue_t dq, dispatch_object_t dou)
        _dispatch_introspection_queue_pop(dq, dou);
 }
 #else
-#define _dispatch_queue_push_notrace _dispatch_queue_push
 #define _dispatch_trace_continuation_push(dq, dou) \
                do { (void)(dq); (void)(dou); } while(0)
 #define _dispatch_trace_continuation_pop(dq, dou) \
@@ -209,27 +181,21 @@ _dispatch_trace_continuation_pop(dispatch_queue_t dq, dispatch_object_t dou)
 
 #if DISPATCH_USE_DTRACE
 static inline dispatch_function_t
-_dispatch_trace_timer_function(dispatch_source_t ds, dispatch_source_refs_t dr)
+_dispatch_trace_timer_function(dispatch_timer_source_refs_t dr)
 {
-       dispatch_continuation_t dc = dr->ds_handler[DS_EVENT_HANDLER];
-       dispatch_function_t func = dc ? dc->dc_func : NULL;
-       if (func == _dispatch_after_timer_callback &&
-                       !(ds->ds_atomic_flags & DSF_CANCELED)) {
-               dc = ds->do_ctxt;
-               func = dc->dc_func != _dispatch_call_block_and_release ? dc->dc_func :
-                               dc->dc_ctxt ? _dispatch_Block_invoke(dc->dc_ctxt) : NULL;
-       }
-       return func;
+       dispatch_continuation_t dc;
+       dc = os_atomic_load(&dr->ds_handler[DS_EVENT_HANDLER], relaxed);
+       return dc ? dc->dc_func : NULL;
 }
 
 DISPATCH_ALWAYS_INLINE
 static inline dispatch_trace_timer_params_t
-_dispatch_trace_timer_params(uintptr_t ident,
+_dispatch_trace_timer_params(dispatch_clock_t clock,
                struct dispatch_timer_source_s *values, uint64_t deadline,
                dispatch_trace_timer_params_t params)
 {
-       #define _dispatch_trace_time2nano3(t) (DISPATCH_TIMER_KIND(ident) \
-                       == DISPATCH_TIMER_KIND_MACH ? _dispatch_time_mach2nano(t) : (t))
+       #define _dispatch_trace_time2nano3(t) \
+                       (clock == DISPATCH_CLOCK_MACH ? _dispatch_time_mach2nano(t) : (t))
        #define _dispatch_trace_time2nano2(v, t) ({ uint64_t _t = (t); \
                        (v) >= INT64_MAX ? -1ll : (int64_t)_dispatch_trace_time2nano3(_t);})
        #define _dispatch_trace_time2nano(v) ({ uint64_t _t; \
@@ -238,14 +204,13 @@ _dispatch_trace_timer_params(uintptr_t ident,
        if (deadline) {
                params->deadline = (int64_t)deadline;
        } else {
-               uint64_t now = (DISPATCH_TIMER_KIND(ident) ==
-                               DISPATCH_TIMER_KIND_MACH ? _dispatch_absolute_time() :
-                                _dispatch_get_nanoseconds());
+               uint64_t now = _dispatch_time_now(clock);
                params->deadline = _dispatch_trace_time2nano2(values->target,
                                values->target < now ? 0 : values->target - now);
        }
+       uint64_t leeway = values->deadline - values->target;
        params->interval = _dispatch_trace_time2nano(values->interval);
-       params->leeway = _dispatch_trace_time2nano(values->leeway);
+       params->leeway = _dispatch_trace_time2nano(leeway);
        return params;
 }
 
@@ -258,51 +223,52 @@ _dispatch_trace_timer_configure_enabled(void)
 
 DISPATCH_ALWAYS_INLINE
 static inline void
-_dispatch_trace_timer_configure(dispatch_source_t ds, uintptr_t ident,
+_dispatch_trace_timer_configure(dispatch_source_t ds, dispatch_clock_t clock,
                struct dispatch_timer_source_s *values)
 {
+       dispatch_timer_source_refs_t dr = ds->ds_timer_refs;
        struct dispatch_trace_timer_params_s params;
-       DISPATCH_TIMER_CONFIGURE(ds, _dispatch_trace_timer_function(ds,
-                       ds->ds_refs), _dispatch_trace_timer_params(ident, values, 0,
-                       &params));
+       DISPATCH_TIMER_CONFIGURE(ds, _dispatch_trace_timer_function(dr),
+                       _dispatch_trace_timer_params(clock, values, 0, &params));
 }
 
 DISPATCH_ALWAYS_INLINE
 static inline void
-_dispatch_trace_timer_program(dispatch_source_refs_t dr, uint64_t deadline)
+_dispatch_trace_timer_program(dispatch_timer_source_refs_t dr, uint64_t deadline)
 {
        if (slowpath(DISPATCH_TIMER_PROGRAM_ENABLED())) {
                if (deadline && dr) {
                        dispatch_source_t ds = _dispatch_source_from_refs(dr);
+                       dispatch_clock_t clock = DISPATCH_TIMER_CLOCK(dr->du_ident);
                        struct dispatch_trace_timer_params_s params;
-                       DISPATCH_TIMER_PROGRAM(ds, _dispatch_trace_timer_function(ds, dr),
-                                       _dispatch_trace_timer_params(ds->ds_ident_hack,
-                                       &ds_timer(dr), deadline, &params));
+                       DISPATCH_TIMER_PROGRAM(ds, _dispatch_trace_timer_function(dr),
+                                       _dispatch_trace_timer_params(clock, &dr->dt_timer,
+                                       deadline, &params));
                }
        }
 }
 
 DISPATCH_ALWAYS_INLINE
 static inline void
-_dispatch_trace_timer_wake(dispatch_source_refs_t dr)
+_dispatch_trace_timer_wake(dispatch_timer_source_refs_t dr)
 {
        if (slowpath(DISPATCH_TIMER_WAKE_ENABLED())) {
                if (dr) {
                        dispatch_source_t ds = _dispatch_source_from_refs(dr);
-                       DISPATCH_TIMER_WAKE(ds, _dispatch_trace_timer_function(ds, dr));
+                       DISPATCH_TIMER_WAKE(ds, _dispatch_trace_timer_function(dr));
                }
        }
 }
 
 DISPATCH_ALWAYS_INLINE
 static inline void
-_dispatch_trace_timer_fire(dispatch_source_refs_t dr, unsigned long data,
-               unsigned long missed)
+_dispatch_trace_timer_fire(dispatch_timer_source_refs_t dr, uint64_t data,
+               uint64_t missed)
 {
        if (slowpath(DISPATCH_TIMER_FIRE_ENABLED())) {
                if (!(data - missed) && dr) {
                        dispatch_source_t ds = _dispatch_source_from_refs(dr);
-                       DISPATCH_TIMER_FIRE(ds, _dispatch_trace_timer_function(ds, dr));
+                       DISPATCH_TIMER_FIRE(ds, _dispatch_trace_timer_function(dr));
                }
        }
 }
@@ -310,8 +276,8 @@ _dispatch_trace_timer_fire(dispatch_source_refs_t dr, unsigned long data,
 #else
 
 #define _dispatch_trace_timer_configure_enabled() false
-#define _dispatch_trace_timer_configure(ds, ident, values) \
-               do { (void)(ds); (void)(ident); (void)(values); } while(0)
+#define _dispatch_trace_timer_configure(ds, clock, values) \
+               do { (void)(ds); (void)(clock); (void)(values); } while(0)
 #define _dispatch_trace_timer_program(dr, deadline) \
                do { (void)(dr); (void)(deadline); } while(0)
 #define _dispatch_trace_timer_wake(dr) \
@@ -321,6 +287,6 @@ _dispatch_trace_timer_fire(dispatch_source_refs_t dr, unsigned long data,
 
 #endif // DISPATCH_USE_DTRACE
 
-#endif // !__OBJC2__ && !defined(__cplusplus)
+#endif // DISPATCH_PURE_C
 
 #endif // __DISPATCH_TRACE__