/* ObjectWindows dynamic handlers from message table 1028:05cc. */ #include "tdkpin_window_messages.h" #include "tdkpin_object_list.h" enum { OBJECT_VMT_OFFSET = 0, OBJECT_STATUS_OFFSET = 2, OBJECT_WINDOW_HANDLE_OFFSET = 4, OBJECT_FLAGS_OFFSET = 0x16, OBJECT_PARENT_OFFSET = 6, WINDOW_DEFAULT_HANDLER_SLOT = 0x0c, WINDOW_MESSAGE_0014_SLOT = 0x10, WINDOW_CAN_CLOSE_SLOT = 0x3c, WINDOW_SCROLL_HANDLER_SLOT = 0x48, APPLICATION_MAIN_WINDOW_OFFSET = 8, APPLICATION_CAN_CLOSE_SLOT = 0x44, WIN16_GWL_STYLE = -16, WIN16_WS_HSCROLL_HIGH = 0x0010, WIN16_WS_VSCROLL_HIGH = 0x0020, WIN16_WM_GETDLGCODE = 0x0087, WIN16_WM_COMMAND = 0x0111, WIN16_DLGC_BUTTON_MASK = 0x0030, WIN16_GWW_ID = -12, DGROUP_TURBO_WINDOW_CLASS_NAME = 0x068c, CHILD_WINDOWED_CALLBACK_OFFSET = 0x0cc7, WINDOW_MDI_CLIENT_SLOT = 0x30, WIN16_WM_MDIDESTROY = 0x0221, WINDOW_SAVED_FOCUS_OFFSET = 0x3f, WINDOW_ATTACHED_OBJECT_OFFSET = 0x3b, WINDOW_WIDTH_OFFSET = 0x2d, WINDOW_HEIGHT_OFFSET = 0x2f, WIN16_WM_LBUTTONUP = 0x0202, }; static Win16FarPtr object_vmt_procedure( Win16FarPtr object, uint16_t slot) { uint16_t vmt = win16_read_u16( win16_far_add_offset(object, OBJECT_VMT_OFFSET)); return win16_read_far_pointer(win16_dgroup_pointer(vmt), slot); } static Win16FarPtr application_main_window(void) { return win16_read_far_pointer( g_object_windows_application, APPLICATION_MAIN_WINDOW_OFFSET); } static void call_default_handler( Win16FarPtr window, ObjectWindowsMessage *message) { win16_call_object_message_handler( object_vmt_procedure(window, WINDOW_DEFAULT_HANDLER_SLOT), window, message); } static Win16FarPtr attached_object(Win16FarPtr window) { return win16_read_far_pointer(window, WINDOW_ATTACHED_OBJECT_OFFSET); } static void dispatch_attached_scroll( Win16FarPtr window, ObjectWindowsMessage *message, uint32_t required_style, uint16_t attached_slot) { HWND16 handle = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); uint32_t style = (uint32_t)GetWindowLong16(handle, WIN16_GWL_STYLE); if ((style & required_style) == 0) { win16_call_object_message_handler( object_vmt_procedure(window, WINDOW_SCROLL_HANDLER_SLOT), window, message); return; } Win16FarPtr attached = attached_object(window); if (attached == 0) { call_default_handler(window, message); return; } win16_call_object_scroll_method( object_vmt_procedure(attached, attached_slot), attached, (uint16_t)message->lparam, message->wparam); } /* 1018:1788 -- horizontal scrolling with optional attached controller. */ void object_windows_wm_hscroll_attached( Win16FarPtr window, ObjectWindowsMessage *message) { dispatch_attached_scroll( window, message, 0x00100000u, 0x20); } /* 1018:17f8 -- vertical scrolling with optional attached controller. */ void object_windows_wm_vscroll_attached( Win16FarPtr window, ObjectWindowsMessage *message) { dispatch_attached_scroll( window, message, 0x00200000u, 0x1c); } /* * 1018:1868 -- BeginPaint/EndPaint lifetime around attached +14/+18 and window * +4c virtuals. All three receive the same 32-byte PAINTSTRUCT16 stack object. */ void object_windows_wm_paint_attached( Win16FarPtr window, ObjectWindowsMessage *message) { (void)message; PAINTSTRUCT16 paint; HWND16 handle = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); (void)BeginPaint16(handle, win16_stack_pointer(&paint)); Win16FarPtr attached = attached_object(window); if (attached != 0) { win16_call_object_paint_method( object_vmt_procedure(attached, 0x14), attached, &paint, paint.dc); } win16_call_object_paint_method( object_vmt_procedure(window, 0x4c), window, &paint, paint.dc); if (attached != 0) { win16_call_object_method( object_vmt_procedure(attached, 0x18), attached); } (void)EndPaint16(handle, win16_stack_pointer(&paint)); } /* 1018:18e9 -- attached resize notification and cached outer dimensions. */ void object_windows_wm_size_attached( Win16FarPtr window, ObjectWindowsMessage *message) { Win16FarPtr attached = attached_object(window); if (attached != 0 && message->wparam != 1) { win16_call_object_method( object_vmt_procedure(attached, 0x0c), attached); } if (message->wparam == 0) { RECT16 rectangle; HWND16 handle = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); (void)GetWindowRect16(handle, win16_stack_pointer(&rectangle)); win16_write_u16( window, WINDOW_WIDTH_OFFSET, (uint16_t)(rectangle.right - rectangle.left)); win16_write_u16( window, WINDOW_HEIGHT_OFFSET, (uint16_t)(rectangle.bottom - rectangle.top)); } call_default_handler(window, message); } /* * 1018:1986 -- attached mouse tracking. The original keeps the last/unfilled * MSG contents when PeekMessage is false, so the initial message id is made an * explicit indeterminate word instead of invoking undefined host-C behavior. */ void object_windows_track_mouse_until_button_up( Win16FarPtr window, ObjectWindowsMessage *message) { Win16FarPtr attached = attached_object(window); if (attached != 0 && win16_read_u8(win16_far_add_offset(attached, 0x22)) != 0) { HWND16 handle = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); (void)SetCapture16(handle); MSG16 queued = {.message = win16_indeterminate_u16()}; do { if (PeekMessage16(&queued, 0, 0, 0, 1) != 0) { (void)TranslateMessage16(&queued); (void)DispatchMessage16(&queued); } win16_call_object_u16_method( object_vmt_procedure(attached, 0x24), attached, handle); } while (queued.message != WIN16_WM_LBUTTONUP); (void)ReleaseCapture16(); } call_default_handler(window, message); } /* 1018:0673 — AL=1 exactly when every requested bit is set at object +0x16. */ bool object_windows_has_flags(Win16FarPtr object, uint8_t mask) { uint8_t flags = win16_read_u8( win16_far_add_offset(object, OBJECT_FLAGS_OFFSET)); return (flags & mask) == mask; } /* 1018:05dc — inherited virtual default returning AX=0. */ uint16_t object_windows_zero_word_default(Win16FarPtr object) { (void)object; return 0; } /* 1018:0641 — set or clear a mask in the packed object flag byte at +0x16. */ void object_windows_update_flags( Win16FarPtr object, bool set, uint8_t mask) { Win16FarPtr address = win16_far_add_offset(object, OBJECT_FLAGS_OFFSET); uint8_t flags = win16_read_u8(address); win16_write_u8(address, set ? (uint8_t)(flags | mask) : (uint8_t)(flags & (uint8_t)~mask)); } /* 1018:05f3, 060d, 0627 — fixed-mask compiler wrappers. */ void object_windows_set_flag_1(Win16FarPtr object) { object_windows_update_flags(object, true, 1); } void object_windows_set_flag_4(Win16FarPtr object) { object_windows_update_flags(object, true, 4); } void object_windows_clear_flag_4(Win16FarPtr object) { object_windows_update_flags(object, false, 4); } /* 1018:0f38 — ask the appropriate CanClose virtual and dispose on approval. */ void object_windows_close_if_allowed(Win16FarPtr window) { bool allowed; if (window == application_main_window()) { allowed = win16_call_object_bool_method( object_vmt_procedure( g_object_windows_application, APPLICATION_CAN_CLOSE_SLOT), g_object_windows_application); } else { allowed = win16_call_object_bool_method( object_vmt_procedure(window, WINDOW_CAN_CLOSE_SLOT), window); } if (allowed) { borland_dispose_object(window); } } /* 1018:0f22 — dynamic id 0x0010 (WM_CLOSE). */ void object_windows_wm_close( Win16FarPtr window, ObjectWindowsMessage *message) { (void)message; object_windows_close_if_allowed(window); } /* 1018:0f8d — dynamic id 0x0002 (WM_DESTROY). */ void object_windows_wm_destroy( Win16FarPtr window, ObjectWindowsMessage *message) { if (window == application_main_window()) { PostQuitMessage16(win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET))); } call_default_handler(window, message); } /* 1018:0fcc — dynamic id 0x0082 (WM_NCDESTROY). */ void object_windows_wm_nc_destroy( Win16FarPtr window, ObjectWindowsMessage *message) { HWND16 handle = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); object_windows_unbind_window(handle); call_default_handler(window, message); win16_write_u16(window, OBJECT_WINDOW_HANDLE_OFFSET, 0); } /* 1018:0ffd — dynamic id 0x0006 (WM_ACTIVATE). */ void object_windows_wm_activate( Win16FarPtr window, ObjectWindowsMessage *message) { call_default_handler(window, message); if (message->wparam == 0) { return; } Win16FarPtr active = object_windows_has_flags(window, 1) ? window : 0; object_windows_application_set_active_dialog( g_object_windows_application, active); } /* 1018:1054 — dynamic id 0x0011 (WM_QUERYENDSESSION). */ void object_windows_wm_query_end_session( Win16FarPtr window, ObjectWindowsMessage *message) { bool allowed; if (window == application_main_window()) { allowed = win16_call_object_bool_method( object_vmt_procedure( g_object_windows_application, APPLICATION_CAN_CLOSE_SLOT), g_object_windows_application); } else { allowed = win16_call_object_bool_method( object_vmt_procedure(window, WINDOW_CAN_CLOSE_SLOT), window); } message->result = allowed ? 1 : 0; } /* * 1018:10aa — dynamic id 0x0014. The numeric id and exact behavior are kept * explicit because a stronger source-level OWL method name is not encoded. */ void object_windows_message_0014( Win16FarPtr window, ObjectWindowsMessage *message) { if (window == application_main_window()) { object_windows_close_if_allowed(window); return; } win16_call_object_message_handler( object_vmt_procedure(window, WINDOW_MESSAGE_0014_SLOT), window, message); } static void dispatch_scroll_message( Win16FarPtr window, ObjectWindowsMessage *message, uint16_t style_high_mask) { uint32_t style = (uint32_t)GetWindowLong16( win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)), WIN16_GWL_STYLE); uint16_t style_high = (uint16_t)(style >> 16); uint16_t slot = (style_high & style_high_mask) == 0 ? WINDOW_SCROLL_HANDLER_SLOT : WINDOW_DEFAULT_HANDLER_SLOT; win16_call_object_message_handler( object_vmt_procedure(window, slot), window, message); } /* 1018:0b6c — dynamic id 0x0114 (WM_HSCROLL). */ void object_windows_wm_hscroll( Win16FarPtr window, ObjectWindowsMessage *message) { dispatch_scroll_message( window, message, WIN16_WS_HSCROLL_HIGH); } /* 1018:0b25 — dynamic id 0x0115 (WM_VSCROLL). */ void object_windows_wm_vscroll( Win16FarPtr window, ObjectWindowsMessage *message) { dispatch_scroll_message( window, message, WIN16_WS_VSCROLL_HIGH); } /* * 1018:08f0 — dynamic id 0x0111 (WM_COMMAND). * * Win16 encodes the command id in WPARAM, a control HWND in LOWORD(LPARAM), * and the notification in HIWORD(LPARAM). ObjectWindows maps three numeric * bands into dynamic ids by 16-bit subtraction: command-0x6000, * control-0x8000, and notification-0x7000. */ void object_windows_wm_command( Win16FarPtr window, ObjectWindowsMessage *message) { uint16_t control_window = (uint16_t)message->lparam; uint16_t notification = (uint16_t)((uint32_t)message->lparam >> 16); if (object_windows_has_flags(window, 1) && control_window == 0 && notification == 0) { HWND16 dialog = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); HWND16 control = GetDlgItem16(dialog, (INT16)message->wparam); if (control != 0 && (((uint16_t)SendMessage16( control, WIN16_WM_GETDLGCODE, 0, 0) & WIN16_DLGC_BUTTON_MASK) != 0)) { control_window = control; message->lparam = (LPARAM16)control; } } if (control_window == 0) { if (message->wparam < 0x6000) { HWND16 focus = GetFocus16(); Win16FarPtr target = object_windows_object_from_window(focus); HWND16 owner = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); while (target == 0 && focus != 0 && focus != owner) { focus = GetParent16(focus); target = object_windows_object_from_window(focus); } if (target == 0) { target = window; } object_windows_dispatch_event( 0x10, (uint16_t)(message->wparam - 0x6000u), win16_stack_pointer(message), target); return; } call_default_handler(window, message); return; } HWND16 owner = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); HWND16 child_window = GetDlgItem16(owner, (INT16)message->wparam); Win16FarPtr child = object_windows_object_from_window(child_window); if (child != 0 && notification < 0x1000) { object_windows_dispatch_event( 0x18, (uint16_t)(notification - 0x7000u), win16_stack_pointer(message), child); return; } if (message->wparam < 0x1000) { object_windows_dispatch_event( 0x14, (uint16_t)(message->wparam - 0x8000u), win16_stack_pointer(message), window); return; } win16_call_object_message_handler( object_vmt_procedure(window, 0x14), window, message); } /* 1018:0d6a — shared TWindow VMT +0x2c class-name provider. */ Win16FarPtr object_windows_turbo_window_class_name(Win16FarPtr window) { (void)window; return win16_dgroup_pointer(DGROUP_TURBO_WINDOW_CLASS_NAME); } /* * 1018:0a85 — VMT +0x48 shared by WM_HSCROLL/WM_VSCROLL. * HIWORD(LPARAM) identifies the control window. Bound controls dispatch their * notification as id-0x7000; native controls use GWW_ID and id-0x8000. */ void object_windows_route_scroll_notification( Win16FarPtr window, ObjectWindowsMessage *message) { HWND16 control = (HWND16)((uint32_t)message->lparam >> 16); if (control == 0) { call_default_handler(window, message); return; } Win16FarPtr child = object_windows_object_from_window(control); if (child != 0) { object_windows_dispatch_event( 0x18, (uint16_t)(message->wparam - 0x7000u), win16_stack_pointer(message), child); return; } uint16_t control_id = GetWindowWord16(control, WIN16_GWW_ID); if (control_id < 0x1000) { object_windows_dispatch_event( 0x14, (uint16_t)(control_id - 0x8000u), win16_stack_pointer(message), window); return; } win16_call_object_message_handler( object_vmt_procedure(window, 0x14), window, message); } /* * 1018:0bb3 — select a command target from the event HWND, explicit parent * object (+6/+8), or HWND property lookup. A missing/self target falls back to * the current window's VMT +0x0c; otherwise id WPARAM-0x6000 is dispatched. */ void object_windows_route_command_target( Win16FarPtr window, ObjectWindowsMessage *message) { Win16FarPtr target = 0; HWND16 own_window = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); if (message->window != own_window) { target = win16_read_far_pointer(window, OBJECT_PARENT_OFFSET); if (target == 0) { target = object_windows_object_from_window(message->window); } } if (target == 0) { call_default_handler(window, message); return; } object_windows_dispatch_event( 0x10, (uint16_t)(message->wparam - 0x6000u), win16_stack_pointer(message), target); } /* * 1018:0c59 — forward to the explicit parent object. WM_COMMAND uses WPARAM; * every other message derives the dynamic id from this window's GWW_ID. */ void object_windows_forward_event_to_parent( Win16FarPtr window, ObjectWindowsMessage *message) { Win16FarPtr parent = win16_read_far_pointer(window, OBJECT_PARENT_OFFSET); if (parent == 0) { return; } uint16_t id = message->message == WIN16_WM_COMMAND ? message->wparam : GetWindowWord16( win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)), WIN16_GWW_ID); object_windows_dispatch_event( 0x14, (uint16_t)(id - 0x8000u), win16_stack_pointer(message), parent); } /* * 1018:0ce7 — mark all windowed children, then destroy the native HWND. * Flag 8 selects MDI destruction: the parent VMT +0x30 getter is deliberately * called twice, and the second returned client HWND receives WM_MDIDESTROY. */ void object_windows_destroy_native_window(Win16FarPtr window) { HWND16 handle = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); if (handle == 0) { return; } object_windows_for_each_child( window, win16_relocated_code_pointer(4, CHILD_WINDOWED_CALLBACK_OFFSET)); if (object_windows_has_flags(window, 8)) { Win16FarPtr parent = win16_read_far_pointer(window, OBJECT_PARENT_OFFSET); uint16_t parent_vmt = win16_read_u16(parent); Win16FarPtr getter = win16_read_far_pointer( win16_dgroup_pointer(parent_vmt), WINDOW_MDI_CLIENT_SLOT); if (win16_call_object_far_method(getter, parent) != 0) { Win16FarPtr client = win16_call_object_far_method(getter, parent); HWND16 client_window = win16_read_u16(win16_far_add_offset( client, OBJECT_WINDOW_HANDLE_OFFSET)); (void)SendMessage16( client_window, WIN16_WM_MDIDESTROY, handle, 0); return; } } (void)DestroyWindow16(handle); } /* * 1018:0e46 — register an ObjectWindows class only when GetClassInfo cannot * find it. VMT +0x2c returns the far class name and +0x34 fills WNDCLASS16. */ bool object_windows_register_class(Win16FarPtr window) { uint16_t vmt = win16_read_u16(window); Win16FarPtr class_name_proc = win16_read_far_pointer(win16_dgroup_pointer(vmt), 0x2c); Win16FarPtr class_name = win16_call_object_far_method(class_name_proc, window); WNDCLASS16 window_class; if (GetClassInfo16( g_win16_instance, class_name, &window_class) != 0) { return true; } Win16FarPtr builder = win16_read_far_pointer(win16_dgroup_pointer(vmt), 0x34); win16_call_object_wndclass_method(builder, window, &window_class); return RegisterClass16(&window_class) != 0; } /* 1018:1274 — construct the shared ObjectWindows WNDCLASS16 descriptor. */ void object_windows_build_window_class( Win16FarPtr window, WNDCLASS16 *window_class) { window_class->style = 3; window_class->window_proc = win16_relocated_code_pointer(4, 0x018b); window_class->class_extra_bytes = 0; window_class->window_extra_bytes = 0; window_class->instance = g_win16_instance; window_class->icon = LoadIcon16(0, win16_make_far_pointer(0, 0x7f00)); window_class->cursor = LoadCursor16(0, win16_make_far_pointer(0, 0x7f00)); window_class->background_brush = 6; window_class->menu_name = 0; uint16_t vmt = win16_read_u16(window); Win16FarPtr class_name_proc = win16_read_far_pointer(win16_dgroup_pointer(vmt), 0x2c); window_class->class_name = win16_call_object_far_method(class_name_proc, window); } /* 1018:12f5 — unaligned uint16 virtual field getter at object +0x35. */ uint16_t object_windows_get_field_35(Win16FarPtr window) { return win16_read_u16(win16_far_add_offset(window, 0x35)); } /* 1018:1586 — remember focus only when it is a child of this native HWND. */ void object_windows_remember_child_focus(Win16FarPtr window) { HWND16 focus = GetFocus16(); if (focus == 0) { return; } HWND16 parent = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); if (IsChild16(parent, focus) != 0) { win16_write_u16(window, WINDOW_SAVED_FOCUS_OFFSET, focus); } } /* 1018:1547 — restore a saved child focus when both HWNDs remain suitable. */ void object_windows_restore_child_focus(Win16FarPtr window) { HWND16 saved = win16_read_u16(win16_far_add_offset( window, WINDOW_SAVED_FOCUS_OFFSET)); if (saved == 0 || IsWindow16(saved) == 0) { return; } HWND16 owner = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); if (IsIconic16(owner) == 0) { (void)SetFocus16(saved); } } /* 1018:169d — base WM_ACTIVATE behavior plus dialog focus save/restore. */ void object_windows_wm_activate_with_focus( Win16FarPtr window, ObjectWindowsMessage *message) { object_windows_wm_activate(window, message); if (!object_windows_has_flags(window, 1)) { return; } if (message->wparam == 0) { object_windows_remember_child_focus(window); } else { object_windows_restore_child_focus(window); } } /* 1018:1a0e — SC_MINIMIZE/SC_RESTORE focus handling before default dispatch. */ void object_windows_wm_syscommand_focus( Win16FarPtr window, ObjectWindowsMessage *message) { if (object_windows_has_flags(window, 1)) { if (message->wparam == 0xf020) { object_windows_remember_child_focus(window); } else if (message->wparam == 0xf120) { object_windows_restore_child_focus(window); } } call_default_handler(window, message); } /* 1018:1761 — receiver-only VMT +0x38 hook, then default event handler. */ void object_windows_call_slot_38_then_default( Win16FarPtr window, ObjectWindowsMessage *message) { win16_call_object_method( object_vmt_procedure(window, 0x38), window); call_default_handler(window, message); } /* 1018:1960 — save child focus before forwarding the unchanged event. */ void object_windows_remember_focus_then_default( Win16FarPtr window, ObjectWindowsMessage *message) { object_windows_remember_child_focus(window); call_default_handler(window, message); } /* * 1018:1311 — forward through the original far WNDPROC stored unaligned at * object +0x37/+0x39, then publish DX:AX into message result +0x0a/+0x0c. */ void object_windows_call_original_window_proc( Win16FarPtr window, ObjectWindowsMessage *message) { Win16FarPtr procedure = win16_read_far_pointer(window, 0x37); HWND16 handle = win16_read_u16(win16_far_add_offset( window, OBJECT_WINDOW_HANDLE_OFFSET)); message->result = CallWindowProc16( procedure, handle, message->message, message->wparam, message->lparam); } /* 1008:2c08 — receiver-only VMT +0x38 call; event argument is ignored. */ void object_windows_call_slot_38( Win16FarPtr window, ObjectWindowsMessage *message) { (void)message; win16_call_object_method( object_vmt_procedure(window, 0x38), window); } /* 1008:2cd9 — dialog default handler: set the 32-bit result to zero. */ void object_windows_zero_message_result( Win16FarPtr window, ObjectWindowsMessage *message) { (void)window; message->result = 0; } /* * 1008:2c1f -- query whether session termination must be rejected. The main * window delegates to TApplication.CanClose at VMT +44; other windows use * their own CanClose at +3c. The message result is the exact logical inverse. */ void object_windows_query_end_session_result( Win16FarPtr window, ObjectWindowsMessage *message) { Win16FarPtr receiver = window; uint16_t slot = 0x3c; if (window == win16_read_far_pointer( g_object_windows_application, 8)) { receiver = g_object_windows_application; slot = 0x44; } uint16_t vmt = win16_read_u16(receiver); Win16FarPtr procedure = win16_read_far_pointer(win16_dgroup_pointer(vmt), slot); bool can_close = win16_call_object_bool_method(procedure, receiver); message->result = can_close ? 0 : 1; } /* * 1008:2c83 -- focus the HWND in message.wParam, recover its ObjectWindows * object, and invoke VMT +0c on the optional unaligned far child at +0x43. * The process marker is set on every path and has no reader in this image. */ void object_windows_focus_message( Win16FarPtr ignored, ObjectWindowsMessage *message) { (void)ignored; (void)SetFocus16(message->wparam); Win16FarPtr window = object_windows_object_from_window(message->wparam); if (window != 0) { Win16FarPtr attached = win16_read_far_pointer(window, 0x43); if (attached != 0) { uint16_t vmt = win16_read_u16(attached); Win16FarPtr procedure = win16_read_far_pointer(win16_dgroup_pointer(vmt), 0x0c); win16_call_object_method(procedure, attached); } } g_object_windows_focus_event_marker = 1; } /* 1018:0c3d — generated receiver/event forwarding call to VMT +0x0c. */ void object_windows_forward_default( Win16FarPtr window, ObjectWindowsMessage *message) { call_default_handler(window, message); } /* 1018:0cc7 — set object flag 4 only after field +4 becomes nonzero. */ void object_windows_set_flag_4_if_windowed( uint16_t ignored, Win16FarPtr object) { (void)ignored; if (win16_read_u16(win16_far_add_offset( object, OBJECT_WINDOW_HANDLE_OFFSET)) != 0) { object_windows_set_flag_4(object); } }