macOS RAII trace guards (#2150)

* Add TraceGuard to make tracing simpler

* Add SharedStateMutexGuard to make tracing simpler

* Add trace_scope macro

* Add missing let binding in trace_scope!
This commit is contained in:
Mads Marquart 2022-01-23 21:35:26 +01:00 committed by GitHub
parent 51bb6b751e
commit 9229e2d88b
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
7 changed files with 176 additions and 135 deletions

View file

@ -301,7 +301,7 @@ extern "C" fn init_with_winit(this: &Object, _sel: Sel, state: *mut c_void) -> i
}
extern "C" fn view_did_move_to_window(this: &Object, _sel: Sel) {
trace!("Triggered `viewDidMoveToWindow`");
trace_scope!("viewDidMoveToWindow");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -319,10 +319,10 @@ extern "C" fn view_did_move_to_window(this: &Object, _sel: Sel) {
];
state.tracking_rect = Some(tracking_rect);
}
trace!("Completed `viewDidMoveToWindow`");
}
extern "C" fn frame_did_change(this: &Object, _sel: Sel, _event: id) {
trace_scope!("frameDidChange:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -344,6 +344,7 @@ extern "C" fn frame_did_change(this: &Object, _sel: Sel, _event: id) {
}
extern "C" fn draw_rect(this: &Object, _sel: Sel, rect: NSRect) {
trace_scope!("drawRect:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -356,6 +357,7 @@ extern "C" fn draw_rect(this: &Object, _sel: Sel, rect: NSRect) {
}
extern "C" fn accepts_first_responder(_this: &Object, _sel: Sel) -> BOOL {
trace_scope!("acceptsFirstResponder");
YES
}
@ -363,10 +365,12 @@ extern "C" fn accepts_first_responder(_this: &Object, _sel: Sel) -> BOOL {
// IMKInputSession [0x7fc573576ff0 presentFunctionRowItemTextInputViewWithEndpoint:completionHandler:] : [self textInputContext]=0x7fc573558e10 *NO* NSRemoteViewController to client, NSError=Error Domain=NSCocoaErrorDomain Code=4099 "The connection from pid 0 was invalidated from this process." UserInfo={NSDebugDescription=The connection from pid 0 was invalidated from this process.}, com.apple.inputmethod.EmojiFunctionRowItem
// TODO: Add an API extension for using `NSTouchBar`
extern "C" fn touch_bar(_this: &Object, _sel: Sel) -> BOOL {
trace_scope!("touchBar");
NO
}
extern "C" fn reset_cursor_rects(this: &Object, _sel: Sel) {
trace_scope!("resetCursorRects");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -386,20 +390,18 @@ extern "C" fn reset_cursor_rects(this: &Object, _sel: Sel) {
}
extern "C" fn has_marked_text(this: &Object, _sel: Sel) -> BOOL {
trace_scope!("hasMarkedText");
unsafe {
trace!("Triggered `hasMarkedText`");
let marked_text: id = *this.get_ivar("markedText");
trace!("Completed `hasMarkedText`");
(marked_text.length() > 0) as BOOL
}
}
extern "C" fn marked_range(this: &Object, _sel: Sel) -> NSRange {
trace_scope!("markedRange");
unsafe {
trace!("Triggered `markedRange`");
let marked_text: id = *this.get_ivar("markedText");
let length = marked_text.length();
trace!("Completed `markedRange`");
if length > 0 {
NSRange::new(0, length - 1)
} else {
@ -409,8 +411,7 @@ extern "C" fn marked_range(this: &Object, _sel: Sel) -> NSRange {
}
extern "C" fn selected_range(_this: &Object, _sel: Sel) -> NSRange {
trace!("Triggered `selectedRange`");
trace!("Completed `selectedRange`");
trace_scope!("selectedRange");
util::EMPTY_RANGE
}
@ -421,7 +422,7 @@ extern "C" fn set_marked_text(
_selected_range: NSRange,
_replacement_range: NSRange,
) {
trace!("Triggered `setMarkedText`");
trace_scope!("setMarkedText:selectedRange:replacementRange:");
unsafe {
let marked_text_ref: &mut id = this.get_mut_ivar("markedText");
let _: () = msg_send![(*marked_text_ref), release];
@ -434,11 +435,10 @@ extern "C" fn set_marked_text(
};
*marked_text_ref = marked_text;
}
trace!("Completed `setMarkedText`");
}
extern "C" fn unmark_text(this: &Object, _sel: Sel) {
trace!("Triggered `unmarkText`");
trace_scope!("unmarkText");
unsafe {
let marked_text: id = *this.get_ivar("markedText");
let mutable_string = marked_text.mutableString();
@ -448,12 +448,10 @@ extern "C" fn unmark_text(this: &Object, _sel: Sel) {
let input_context: id = msg_send![this, inputContext];
let _: () = msg_send![input_context, discardMarkedText];
}
trace!("Completed `unmarkText`");
}
extern "C" fn valid_attributes_for_marked_text(_this: &Object, _sel: Sel) -> id {
trace!("Triggered `validAttributesForMarkedText`");
trace!("Completed `validAttributesForMarkedText`");
trace_scope!("validAttributesForMarkedText");
unsafe { msg_send![class!(NSArray), array] }
}
@ -463,14 +461,12 @@ extern "C" fn attributed_substring_for_proposed_range(
_range: NSRange,
_actual_range: *mut c_void, // *mut NSRange
) -> id {
trace!("Triggered `attributedSubstringForProposedRange`");
trace!("Completed `attributedSubstringForProposedRange`");
trace_scope!("attributedSubstringForProposedRange:actualRange:");
nil
}
extern "C" fn character_index_for_point(_this: &Object, _sel: Sel, _point: NSPoint) -> NSUInteger {
trace!("Triggered `characterIndexForPoint`");
trace!("Completed `characterIndexForPoint`");
trace_scope!("characterIndexForPoint:");
0
}
@ -480,8 +476,8 @@ extern "C" fn first_rect_for_character_range(
_range: NSRange,
_actual_range: *mut c_void, // *mut NSRange
) -> NSRect {
trace_scope!("firstRectForCharacterRange:actualRange:");
unsafe {
trace!("Triggered `firstRectForCharacterRange`");
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
let (x, y) = state.ime_spot.unwrap_or_else(|| {
@ -493,13 +489,12 @@ extern "C" fn first_rect_for_character_range(
let y = util::bottom_left_to_top_left(content_rect);
(x, y)
});
trace!("Completed `firstRectForCharacterRange`");
NSRect::new(NSPoint::new(x as _, y as _), NSSize::new(0.0, 0.0))
}
}
extern "C" fn insert_text(this: &Object, _sel: Sel, string: id, _replacement_range: NSRange) {
trace!("Triggered `insertText`");
trace_scope!("insertText:replacementRange:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -530,11 +525,10 @@ extern "C" fn insert_text(this: &Object, _sel: Sel, string: id, _replacement_ran
AppState::queue_events(events);
}
trace!("Completed `insertText`");
}
extern "C" fn do_command_by_selector(this: &Object, _sel: Sel, command: Sel) {
trace!("Triggered `doCommandBySelector`");
trace_scope!("doCommandBySelector:");
// Basically, we're sent this message whenever a keyboard event that doesn't generate a "human readable" character
// happens, i.e. newlines, tabs, and Ctrl+C.
unsafe {
@ -567,7 +561,6 @@ extern "C" fn do_command_by_selector(this: &Object, _sel: Sel, command: Sel) {
AppState::queue_events(events);
}
trace!("Completed `doCommandBySelector`");
}
fn get_characters(event: id, ignore_modifiers: bool) -> String {
@ -639,7 +632,7 @@ fn update_potentially_stale_modifiers(state: &mut ViewState, event: id) {
}
extern "C" fn key_down(this: &Object, _sel: Sel, event: id) {
trace!("Triggered `keyDown`");
trace_scope!("keyDown:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -694,11 +687,10 @@ extern "C" fn key_down(this: &Object, _sel: Sel, event: id) {
let _: () = msg_send![this, interpretKeyEvents: array];
}
}
trace!("Completed `keyDown`");
}
extern "C" fn key_up(this: &Object, _sel: Sel, event: id) {
trace!("Triggered `keyUp`");
trace_scope!("keyUp:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -725,11 +717,10 @@ extern "C" fn key_up(this: &Object, _sel: Sel, event: id) {
AppState::queue_event(EventWrapper::StaticEvent(window_event));
}
trace!("Completed `keyUp`");
}
extern "C" fn flags_changed(this: &Object, _sel: Sel, event: id) {
trace!("Triggered `flagsChanged`");
trace_scope!("flagsChanged:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -786,10 +777,10 @@ extern "C" fn flags_changed(this: &Object, _sel: Sel, event: id) {
event: WindowEvent::ModifiersChanged(state.modifiers),
}));
}
trace!("Completed `flagsChanged`");
}
extern "C" fn insert_tab(this: &Object, _sel: Sel, _sender: id) {
trace_scope!("insertTab:");
unsafe {
let window: id = msg_send![this, window];
let first_responder: id = msg_send![window, firstResponder];
@ -801,6 +792,7 @@ extern "C" fn insert_tab(this: &Object, _sel: Sel, _sender: id) {
}
extern "C" fn insert_back_tab(this: &Object, _sel: Sel, _sender: id) {
trace_scope!("insertBackTab:");
unsafe {
let window: id = msg_send![this, window];
let first_responder: id = msg_send![window, firstResponder];
@ -814,7 +806,7 @@ extern "C" fn insert_back_tab(this: &Object, _sel: Sel, _sender: id) {
// Allows us to receive Cmd-. (the shortcut for closing a dialog)
// https://bugs.eclipse.org/bugs/show_bug.cgi?id=300620#c6
extern "C" fn cancel_operation(this: &Object, _sel: Sel, _sender: id) {
trace!("Triggered `cancelOperation`");
trace_scope!("cancelOperation:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -844,7 +836,6 @@ extern "C" fn cancel_operation(this: &Object, _sel: Sel, _sender: id) {
AppState::queue_event(EventWrapper::StaticEvent(window_event));
}
trace!("Completed `cancelOperation`");
}
fn mouse_click(this: &Object, event: id, button: MouseButton, button_state: ElementState) {
@ -869,31 +860,37 @@ fn mouse_click(this: &Object, event: id, button: MouseButton, button_state: Elem
}
extern "C" fn mouse_down(this: &Object, _sel: Sel, event: id) {
trace_scope!("mouseDown:");
mouse_motion(this, event);
mouse_click(this, event, MouseButton::Left, ElementState::Pressed);
}
extern "C" fn mouse_up(this: &Object, _sel: Sel, event: id) {
trace_scope!("mouseUp:");
mouse_motion(this, event);
mouse_click(this, event, MouseButton::Left, ElementState::Released);
}
extern "C" fn right_mouse_down(this: &Object, _sel: Sel, event: id) {
trace_scope!("rightMouseDown:");
mouse_motion(this, event);
mouse_click(this, event, MouseButton::Right, ElementState::Pressed);
}
extern "C" fn right_mouse_up(this: &Object, _sel: Sel, event: id) {
trace_scope!("rightMouseUp:");
mouse_motion(this, event);
mouse_click(this, event, MouseButton::Right, ElementState::Released);
}
extern "C" fn other_mouse_down(this: &Object, _sel: Sel, event: id) {
trace_scope!("otherMouseDown:");
mouse_motion(this, event);
mouse_click(this, event, MouseButton::Middle, ElementState::Pressed);
}
extern "C" fn other_mouse_up(this: &Object, _sel: Sel, event: id) {
trace_scope!("otherMouseUp:");
mouse_motion(this, event);
mouse_click(this, event, MouseButton::Middle, ElementState::Released);
}
@ -941,6 +938,8 @@ fn mouse_motion(this: &Object, event: id) {
}
}
// No tracing on these because that would be overly verbose
extern "C" fn mouse_moved(this: &Object, _sel: Sel, event: id) {
mouse_motion(this, event);
}
@ -958,7 +957,7 @@ extern "C" fn other_mouse_dragged(this: &Object, _sel: Sel, event: id) {
}
extern "C" fn mouse_entered(this: &Object, _sel: Sel, _event: id) {
trace!("Triggered `mouseEntered`");
trace_scope!("mouseEntered:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -972,11 +971,10 @@ extern "C" fn mouse_entered(this: &Object, _sel: Sel, _event: id) {
AppState::queue_event(EventWrapper::StaticEvent(enter_event));
}
trace!("Completed `mouseEntered`");
}
extern "C" fn mouse_exited(this: &Object, _sel: Sel, _event: id) {
trace!("Triggered `mouseExited`");
trace_scope!("mouseExited:");
unsafe {
let state_ptr: *mut c_void = *this.get_ivar("winitState");
let state = &mut *(state_ptr as *mut ViewState);
@ -990,11 +988,10 @@ extern "C" fn mouse_exited(this: &Object, _sel: Sel, _event: id) {
AppState::queue_event(EventWrapper::StaticEvent(window_event));
}
trace!("Completed `mouseExited`");
}
extern "C" fn scroll_wheel(this: &Object, _sel: Sel, event: id) {
trace!("Triggered `scrollWheel`");
trace_scope!("scrollWheel:");
mouse_motion(this, event);
@ -1043,11 +1040,10 @@ extern "C" fn scroll_wheel(this: &Object, _sel: Sel, event: id) {
AppState::queue_event(EventWrapper::StaticEvent(device_event));
AppState::queue_event(EventWrapper::StaticEvent(window_event));
}
trace!("Completed `scrollWheel`");
}
extern "C" fn pressure_change_with_event(this: &Object, _sel: Sel, event: id) {
trace!("Triggered `pressureChangeWithEvent`");
trace_scope!("pressureChangeWithEvent:");
mouse_motion(this, event);
@ -1069,16 +1065,17 @@ extern "C" fn pressure_change_with_event(this: &Object, _sel: Sel, event: id) {
AppState::queue_event(EventWrapper::StaticEvent(window_event));
}
trace!("Completed `pressureChangeWithEvent`");
}
// Allows us to receive Ctrl-Tab and Ctrl-Esc.
// Note that this *doesn't* help with any missing Cmd inputs.
// https://github.com/chromium/chromium/blob/a86a8a6bcfa438fa3ac2eba6f02b3ad1f8e0756f/ui/views/cocoa/bridged_content_view.mm#L816
extern "C" fn wants_key_down_for_event(_this: &Object, _sel: Sel, _event: id) -> BOOL {
trace_scope!("_wantsKeyDownForEvent:");
YES
}
extern "C" fn accepts_first_mouse(_this: &Object, _sel: Sel, _event: id) -> BOOL {
trace_scope!("acceptsFirstMouse:");
YES
}