swiftoslogcinterop

Can't create the OSLog activity on Swift


I want to use the OSLog activities to structure my logs but I stuck with a problem of absence needed activity constants on Swift such as OS_ACTIVITY_CURRENT and OS_ACTIVITY_NONE and I have an error when I try to create an activity:

let activity = _os_activity_create(dso, strdup(name), 
OS_ACTIVITY_CURRENT, // Error: Static member 'OS_ACTIVITY_CURRENT' cannot be used on instance of type 'OSLogOutput'
OS_ACTIVITY_FLAG_DEFAULT)

os.activity framework has descriptions of activity constants without any definitions (but defines the activity flags OS_ACTIVITY_FLAG_DEFAULT, OS_ACTIVITY_FLAG_DETACHED, OS_ACTIVITY_FLAG_IF_NONE_PRESENT):

/*!
 * @const OS_ACTIVITY_CURRENT
 *
 * @discussion
 * Create activity and links to the current activity if one is present.
 * If no activity is present it is treated as if it is detached.
 */

If we look in ObjC headers <os/activity.h> we can find these constants:

#define OS_ACTIVITY_NONE OS_OBJECT_GLOBAL_OBJECT(os_activity_t, _os_activity_none)
#define OS_ACTIVITY_CURRENT OS_OBJECT_GLOBAL_OBJECT(os_activity_t, _os_activity_current)

It looks like that OSLog is limited on Swift so how to work with OSLog activities or where can I find the constants?


Solution

  • After some research I've found that OS_ACTIVITY_CURRENT and OS_ACTIVITY_NONE can be dynamically loaded using C-Interoperability since it is not exposed to Swift:

    static let RTLD_DEFAULT = UnsafeMutableRawPointer(bitPattern: -2)
    static let OS_ACTIVITY_NONE = unsafeBitCast(dlsym(RTLD_DEFAULT, "_os_activity_none"), to: os_activity_t.self)
    static let OS_ACTIVITY_CURRENT = unsafeBitCast(dlsym(RTLD_DEFAULT, "_os_activity_current"), to: os_activity_t.self)
    

    But it still looks weird why os.log framework provides API but doesn't the needed constants.

    Thanks to https://nsscreencast.com/episodes/347-activity-tracing-in-swift