LSDTrip - Take a ride down the LaunchServices.framework rabbithole

What is this?

(yet another) simple command line utility, which can be used to explore the lesser known reaches of LaunchServices.framework - an allegedly "Public" Framework which even has headers - but still hides the really swell functionality in undocumented calls.

The tool behaves differently on MacOS and the iOS variants. In the former, you have full LaunchServices APIs, so it uses LS* calls (re-exported by CoreServices.framework. In the iOS variants, however, MobileCoreServices.framework provides LSApplication[Workspace/Proxy]. Which explains the messy performSelector in the code - I wanted to do this in pure C, but ended up resorting to Obj-c eventually.

This is (somewhat messy) open source, so you can learn a lot on how to use these many useful functions, like finding which app is in the foreground/visible, dumping info, finding item claims, etc..

Examples

All flavors:

Usage: lsdtrip [apps|plugins] [-v]
                app _bundle_id_ (implies -v for this app)
                whohas _url_ 
                types
                dump

MacOS:

 
               app _bundle_id_ (implies -v for this app)
                front [-v]
                visible
                listen          (Get app launch/foreground notifications - cool)
		shmem
                metainfo
                [app|memory|notification|port|session]status
                whohas _url_ 
                types
                dump

After reversing the shiznits out of lsappinfo(8), MacOS's hidden gem, I replicated its best functionality, including some undocumented (the ...stati calls up there). This provides great samples on how to get the frontmost application (which will be the Terminal usually, but you can prepend sleep 5; before lsdtrip and switch app to test this, as well as the visible application list.

morpheus@Zephyr (~)$ lsappinfo visibleProcessList
ASN:0x0-0x19019-"Terminal": ASN:0x0-0x4feefea-"Safari": 
ASN:0x0-0x518417f-"Screen_Sharing": ASN:0x0-0x1f01f-"Finder": 
ASN:0x0-0x1b01b-"VMware_Fusion": ASN:0x0-0x2835833-"iTunes":
@Zephyr (~)$ lsdtrip visible
0x0-0x19019  /Applications/Utilities/Terminal.app/Contents/MacOS/Terminal
0x0-0x4feefea /Applications/Safari.app/Contents/MacOS/Safari
0x0-0x518417f /System/Library/CoreServices/Applications/Screen Sharing.app/Contents/MacOS/Screen Sharing
0x0-0x1f01f  /System/Library/CoreServices/Finder.app/Contents/MacOS/Finder
0x0-0x1b01b  /Applications/VMware Fusion.app/Contents/MacOS/VMware Fusion
0x0-0x2835833 /Applications/iTunes.app/Contents/MacOS/iTunes

A not-so-new feature which was just disabled for the longest time is "listen", which registers a notification handler for application lifecycle and visibility events:

# Foreground notification
Notification Received:
	CFBundleIdentifier: com.apple.Terminal
	LSFrontApplicationSeed: 299
	LSASN: 0x0-0xa00a
	ApplicationType: Foreground
	LSMenuBarOwnerApplicationSeed: 290
	LSOtherASN: 0x0-0x9009
	LSMenuBarOwnerASN: 0x0-0xa00a
# App startup notification

morpheus@Zephyr (~)$ lsdtrip listen
Notification Received:
	CFBundlePackageType: APPL
	ChangeCount: 525
	LSLaunchedByLaunchServices: true
	DTPlatformVersion: GM
	LSApplicationHasRegistered: true
	NSSupportsSuddenTermination: true
	DTSDKBuild: 17A358a
	NSAppleScriptEnabled: true
	LSApplicationReadyToBeFrontableKey: true
	NSPrincipalClass: MailApp
	LSExecutableFilenameLowerCaseKey: mail
	MailURLShareSupported: true
	BundleIdentifierLowerCase: com.apple.mail
	NSMainNibFile: MainMenu
	LSLaunchedWithLaunchD: true
	LSHasLocalizedDisplayName: true
	LSBundlePathDeviceID: 16777221
	LSASN: 0x0-0x5e05e
	NSServices[0]:  (dict)
		NSMessage: mailSelection
		NSPortName: Mail
			NSSendTypes[0]: NSRTFDPboardType
...
# App killed (by -15)
Notification Received:
	CFBundlePackageType: APPL
	ChangeCount: 529
	LSLaunchedByLaunchServices: true
	DTPlatformVersion: GM
	LSApplicationHasRegistered: true
	DTSDKBuild: 17A347
	NSAppleScriptEnabled: true
	LSApplicationReadyToBeFrontableKey: true
	NSPrincipalClass: NSApplication
	LSExecutableFilenameLowerCaseKey: notes
	BundleIdentifierLowerCase: com.apple.notes
	NSMainNibFile: MainMenu
	LSLaunchedWithLaunchD: true
	LSBundlePathDeviceID: 16777221
	CFBundleDisplayName: Notes
	LSASN: 0x0-0x55055
	LSExitStatus: 15
	LSApplicationHasSignalledItIsReady: true

Another useful feature is shmem which dumps the shared memory provided by launchservicesd. This shared memory region (usually 4 pages) captures the visibility state of all applications, and helps determine the frontmost application and z-indices (though there are LS* wrappers to do all that as well).

metainfo is really interesting, as are the various stati. Tons of output, so try it for yourself. Haven't found *OS counterparts for this , yet.

*OS:

Usage: lsdtrip [apps|plugins|publicurls|privateurls] [-v]
                launch _bundle_id_
                advid [clear]

Entitlements:

(and you can always check out The entitlement database if in doubt)

Downloads

License, etc:

As will my other open sources, free - but be so kind as to at least leave the sources intact, give credit, or something. At the very least, don't github this and claim it as your own. People have been doing that, and it's $%#$% annoying and makes me want to quit releasing these things openly.

Code is messy and could seriously use cleanup. I keep updating this as I go along, so wait for those "notyet"s :-)

Comments/Feedback:

Via the Book Forum, please

If you haven't checked out MOXiI Volume I's Table of Contents - give it a glance. It's pretty much final, but I'm always flexible for last minute suggestions (via forum)

Advertisement

  • The next MOXiI Training by Technologeeks is open, and it's on December 11th 2017.