Bug 214245 - Resolve race between IOHIDManager and GameController framework
Summary: Resolve race between IOHIDManager and GameController framework
Status: RESOLVED FIXED
Alias: None
Product: WebKit
Classification: Unclassified
Component: WebCore Misc. (show other bugs)
Version: WebKit Nightly Build
Hardware: Unspecified Unspecified
: P2 Normal
Assignee: Brady Eidson
URL:
Keywords: InRadar
Depends on:
Blocks:
 
Reported: 2020-07-12 19:47 PDT by Brady Eidson
Modified: 2020-07-15 10:10 PDT (History)
5 users (show)

See Also:


Attachments
Patch (18.69 KB, patch)
2020-07-14 15:27 PDT, Brady Eidson
no flags Details | Formatted Diff | Diff
Patch (18.74 KB, patch)
2020-07-14 15:49 PDT, Brady Eidson
no flags Details | Formatted Diff | Diff
Those changes, plus some "make it build on Big Sur" changes (19.07 KB, patch)
2020-07-14 23:26 PDT, Brady Eidson
no flags Details | Formatted Diff | Diff
Other configuration build fixes (3.30 KB, patch)
2020-07-15 09:19 PDT, Brady Eidson
no flags Details | Formatted Diff | Diff
Patch (2.26 KB, patch)
2020-07-15 10:06 PDT, Chris Dumez
no flags Details | Formatted Diff | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Brady Eidson 2020-07-12 19:47:18 PDT
Resolve race between IOHIDManager and GameController framework

There's a race between the IOHIDService being available for an IOHIDDevice, and GameController framework publishing that same device.

This leads us to sometimes show the same gamepad twice - Once through IOHID and once through GCF.

We can shift our HID provider to use IOHIDService directly to resolve this.
Comment 1 Brady Eidson 2020-07-14 15:12:32 PDT
rdar://problem/65554490
Comment 2 Brady Eidson 2020-07-14 15:27:08 PDT
Created attachment 404292 [details]
Patch
Comment 3 Brady Eidson 2020-07-14 15:49:48 PDT
Created attachment 404298 [details]
Patch
Comment 4 Brady Eidson 2020-07-14 17:13:29 PDT
(In reply to Brady Eidson from comment #0)
> Resolve race between IOHIDManager and GameController framework
> 
> There's a race between the IOHIDService being available for an IOHIDDevice,
> and GameController framework publishing that same device.
> 
> This leads us to sometimes show the same gamepad twice - Once through IOHID
> and once through GCF.
> 
> We can shift our HID provider to use IOHIDService directly to resolve this.

BTW ^^^ That wasn't possible. So we're doing the approach in the patch
Comment 5 Tim Horton 2020-07-14 21:59:09 PDT
Comment on attachment 404298 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=404298&action=review

> Source/WebCore/ChangeLog:16
> +        GameControler.framework uses IOHIDServices.

Controller

> Source/WebCore/ChangeLog:42
> +        In my testing, when the service publishes after the devices, it's always wihin 50ms, so the 1s
> +        delay seems sufficient.

Slightly frightening. Do you understand the source of the delay? (if it's, say, fetching something from disk, it might be much longer on some hardware).

> Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.h:59
> +        Yes,
> +        No

Someone debugging later might get quite sad about the order of these values (say, if they cast to bool in logging). Maybe swap them?

> Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.mm:191
> +    Yes,
> +    No,
> +    Maybe,

You've done it again

> Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.mm:268
> +    [matchingAttributes addObject:@{(id)CFSTR(kIOHIDDeviceUsagePageKey) : @(kHIDPage_GenericDesktop), (id)CFSTR(kIOHIDDeviceUsageKey) : @(kHIDUsage_GD_GamePad)}];
> +    [matchingAttributes addObject:@{(id)CFSTR(kIOHIDDeviceUsagePageKey) : @(kHIDPage_GenericDesktop), (id)CFSTR(kIOHIDDeviceUsageKey) : @(kHIDUsage_GD_Joystick)}];

Why are you making CFStrings? Seems like NSString is fine, due to toll-free bridging, no? (and then you can just @() like you do for the what-I-assume-are-NSNumbers)

> Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.mm:270
> +    IOHIDEventSystemClientSetMatchingMultiple(m_eventSystemClient.get(), (__bridge CFArrayRef)(matchingAttributes));

Weird extra parens around matchingAttributes

> Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.mm:275
> +        HIDGamepadProvider::singleton().newGamePadServicePublished();

The leading "new" is triggering my "new or create" instinct. Maybe didPublishNewGamePadService? Or, since we aren't the ones publishing, some other verb?
Comment 6 Brady Eidson 2020-07-14 22:45:42 PDT
(In reply to Tim Horton from comment #5)
> Comment on attachment 404298 [details]
> Patch
> 
> View in context:
> https://bugs.webkit.org/attachment.cgi?id=404298&action=review
> 
> > Source/WebCore/ChangeLog:16
> > +        GameControler.framework uses IOHIDServices.
> 
> Controller
> 
> > Source/WebCore/ChangeLog:42
> > +        In my testing, when the service publishes after the devices, it's always wihin 50ms, so the 1s
> > +        delay seems sufficient.
> 
> Slightly frightening. Do you understand the source of the delay? (if it's,
> say, fetching something from disk, it might be much longer on some hardware).

It's not storage bound.

The "normal" race is simply mach messaging from the kernel coming up to user space through two different mach ports. A truly classic race.

A potential race *is* I/O bound as an atypically behaved physical gamepad device can get itself into this situation by being "weird" over USB/BT.

50ms is "a few ms roundtrip on one of those busses" plus a few kernel->user roundtrips.

We don't expect even that on common, well behaved hardware.

If the physical hardware itself causes a 1s delay...  It is PROBABLY not a piece of hardware GameController framework would handle (PS4, Xbox1, and MFi controllers) which are all known to behave.

tldr; I could construct a physical device to misbehave in this manner on purpose to exceed even the one second delay, but in the real world no such device would be handled by GCF

> 
> > Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.h:59
> > +        Yes,
> > +        No
> 
> Someone debugging later might get quite sad about the order of these values
> (say, if they cast to bool in logging). Maybe swap them?

Yes.

> 
> > Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.mm:191
> > +    Yes,
> > +    No,
> > +    Maybe,
> 
> You've done it again

It's as if my tired brain that fell into the anti-pattern once could fall into it again.

> 
> > Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.mm:268
> > +    [matchingAttributes addObject:@{(id)CFSTR(kIOHIDDeviceUsagePageKey) : @(kHIDPage_GenericDesktop), (id)CFSTR(kIOHIDDeviceUsageKey) : @(kHIDUsage_GD_GamePad)}];
> > +    [matchingAttributes addObject:@{(id)CFSTR(kIOHIDDeviceUsagePageKey) : @(kHIDPage_GenericDesktop), (id)CFSTR(kIOHIDDeviceUsageKey) : @(kHIDUsage_GD_Joystick)}];
> 
> Why are you making CFStrings? Seems like NSString is fine, due to toll-free
> bridging, no? (and then you can just @() like you do for the
> what-I-assume-are-NSNumbers)

Yah 100%.
> 
> > Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.mm:270
> > +    IOHIDEventSystemClientSetMatchingMultiple(m_eventSystemClient.get(), (__bridge CFArrayRef)(matchingAttributes));
> 
> Weird extra parens around matchingAttributes
> 

Yah 100%

> > Source/WebCore/platform/gamepad/mac/HIDGamepadProvider.mm:275
> > +        HIDGamepadProvider::singleton().newGamePadServicePublished();
> 
> The leading "new" is triggering my "new or create" instinct. Maybe
> didPublishNewGamePadService? Or, since we aren't the ones publishing, some
> other verb?

Sure.
Comment 7 Brady Eidson 2020-07-14 23:26:14 PDT
Created attachment 404320 [details]
Those changes, plus some "make it build on Big Sur" changes
Comment 8 EWS 2020-07-15 01:00:17 PDT
Committed r264389: <https://trac.webkit.org/changeset/264389>

All reviewed patches have been landed. Closing bug and clearing flags on attachment 404320 [details].
Comment 9 Brady Eidson 2020-07-15 09:01:21 PDT
This broke release builds on Catalina/Big Sur (due to unused variable),
and non-Apple-Internal builds (due to some missing SPI forward decls)

Fixing both soon.
Comment 10 Brady Eidson 2020-07-15 09:19:23 PDT
Created attachment 404349 [details]
Other configuration build fixes
Comment 11 Brady Eidson 2020-07-15 09:51:55 PDT
EWS isn't doing anything here...
So I doubt the CQ will either.
Comment 12 Chris Dumez 2020-07-15 10:06:47 PDT
Reopening to attach new patch.
Comment 13 Chris Dumez 2020-07-15 10:06:48 PDT
Created attachment 404352 [details]
Patch
Comment 14 Brady Eidson 2020-07-15 10:10:52 PDT
https://trac.webkit.org/changeset/264402/webkit for the OSS build SPI fix
https://trac.webkit.org/changeset/264401/webkit for the release build fix