From patchwork Mon Mar 4 16:49:52 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 10838039 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 13F1017E0 for ; Mon, 4 Mar 2019 16:51:21 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 00EF72ACBF for ; Mon, 4 Mar 2019 16:51:21 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id F17CA2AC9E; Mon, 4 Mar 2019 16:51:20 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.7 required=2.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,MAILING_LIST_MULTI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 59EE22ACDC for ; Mon, 4 Mar 2019 16:51:20 +0000 (UTC) Received: from localhost ([127.0.0.1]:57167 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qoB-0005SQ-K8 for patchwork-qemu-devel@patchwork.kernel.org; Mon, 04 Mar 2019 11:51:19 -0500 Received: from eggs.gnu.org ([209.51.188.92]:52459) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qmy-0004MZ-6A for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:05 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1h0qmx-0005gV-3h for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:04 -0500 Received: from mail-wr1-x435.google.com ([2a00:1450:4864:20::435]:32899) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1h0qmw-0005fk-SW for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:03 -0500 Received: by mail-wr1-x435.google.com with SMTP id i12so6325037wrw.0 for ; Mon, 04 Mar 2019 08:50:02 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=7Kc1Pn/mGVzIiCkYEhD4KuVg7QlLrkOtfZT0u/xpGkA=; b=k2uP13zxLtrbY8fBn8UrJv0Ug/eWuh1IhwYlsVYz+OchyTpVIoC4knRnEuYyzo4fPV vYqJLF1Q+Ap7sxKG4Gisc3j4cgXna/Pw0yUMzavr4YOhZqtwKbeAsnPtEdUZP7dU4BCG /KeAjpVsYKS4uQHh3E9ec6qnOw6vPAU0jffgkVGnga7CIiw6WClLhLnvuyXx2QmcekRt x7EXIzcCc33yQaRP2cYGDqKoZCF7Y0nzkHLglBJK2I/5TS5YQw6gzlwzFB8LmP7G3Rtk VZmBBVMrZoWKEJ7GTO4SKU9YZ3Mr0SdRUMgX0MijmXYyfwqXhCMmU2KABsi0+556j1fo pXDg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=7Kc1Pn/mGVzIiCkYEhD4KuVg7QlLrkOtfZT0u/xpGkA=; b=fb8SMOJdWyRRdMBK2UsP+aUq68/KxT+m/j8vr0mmEFyTHN0+xxA1vq/IWaNXlswc2H t5xWqirMYCz6mJzR3ejTxUv2LUo95A720xrOg48Yb5WMyoaMahduIFpZpFr2rnap2Ewk h2hd7hfuxsXw+3CUcLgHsmRzdNPa+yjcb79T5eutHwzh+n62u+hCgi9QapfQRQEVGs7p o+dFCzALS+Jzm2M3tse2e3dIHLo/zttQYzmfDJknaq6kcTF8omuViywXbmFqjcyf/W46 chxdrMtW6DhYvFDDZ7qdCc9IGivGF6/cWlxqGkGUBGx9EZYQ5m/+ZEM2YkhP+E04E4Q/ Fn2A== X-Gm-Message-State: APjAAAV51fEVD3MZ2QA6QOALedgQ0snZh/k9RIgJwuSU6fQDKt0xOZXM SIdIj7ZkqKK5cazvb50+zt6McRaTIfc= X-Google-Smtp-Source: APXvYqybjJEGnnfz5arGA/fWhL2pTTyhf56QIbnaizrPHr9A5AnqRhJ3XzBdmrX3TuORF+xYINdFXQ== X-Received: by 2002:adf:9167:: with SMTP id j94mr14117313wrj.106.1551718201417; Mon, 04 Mar 2019 08:50:01 -0800 (PST) Received: from orth.archaic.org.uk (orth.archaic.org.uk. [81.2.115.148]) by smtp.gmail.com with ESMTPSA id x74sm7238018wmf.22.2019.03.04.08.50.00 for (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 04 Mar 2019 08:50:00 -0800 (PST) From: Peter Maydell To: qemu-devel@nongnu.org Date: Mon, 4 Mar 2019 16:49:52 +0000 Message-Id: <20190304164958.9362-2-peter.maydell@linaro.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20190304164958.9362-1-peter.maydell@linaro.org> References: <20190304164958.9362-1-peter.maydell@linaro.org> MIME-Version: 1.0 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:4864:20::435 Subject: [Qemu-devel] [PULL 1/7] ui/cocoa: Ensure we have the iothread lock when calling into QEMU X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP The Cocoa UI should run on the main thread; this is enforced in OSX Mojave. In order to be able to run on the main thread, we need to make sure we hold the iothread lock whenever we call into various QEMU UI midlayer functions. Signed-off-by: Peter Maydell Reviewed-by: Roman Bolshakov Tested-by: Roman Bolshakov Message-id: 20190225102433.22401-2-peter.maydell@linaro.org Message-id: 20190214102816.3393-2-peter.maydell@linaro.org --- ui/cocoa.m | 91 ++++++++++++++++++++++++++++++++++++++---------------- 1 file changed, 65 insertions(+), 26 deletions(-) diff --git a/ui/cocoa.m b/ui/cocoa.m index e2567d69466..f1171c48654 100644 --- a/ui/cocoa.m +++ b/ui/cocoa.m @@ -129,6 +129,21 @@ bool stretch_video; NSTextField *pauseLabel; NSArray * supportedImageFileTypes; +// Utility function to run specified code block with iothread lock held +typedef void (^CodeBlock)(void); + +static void with_iothread_lock(CodeBlock block) +{ + bool locked = qemu_mutex_iothread_locked(); + if (!locked) { + qemu_mutex_lock_iothread(); + } + block(); + if (!locked) { + qemu_mutex_unlock_iothread(); + } +} + // Mac to QKeyCode conversion const int mac_to_qkeycode_map[] = { [kVK_ANSI_A] = Q_KEY_CODE_A, @@ -306,6 +321,7 @@ static void handleAnyDeviceErrors(Error * err) - (void) toggleFullScreen:(id)sender; - (void) handleMonitorInput:(NSEvent *)event; - (void) handleEvent:(NSEvent *)event; +- (void) handleEventLocked:(NSEvent *)event; - (void) setAbsoluteEnabled:(BOOL)tIsAbsoluteEnabled; /* The state surrounding mouse grabbing is potentially confusing. * isAbsoluteEnabled tracks qemu_input_is_absolute() [ie "is the emulated @@ -649,8 +665,14 @@ QemuCocoaView *cocoaView; - (void) handleEvent:(NSEvent *)event { - COCOA_DEBUG("QemuCocoaView: handleEvent\n"); + with_iothread_lock(^{ + [self handleEventLocked:event]; + }); +} +- (void) handleEventLocked:(NSEvent *)event +{ + COCOA_DEBUG("QemuCocoaView: handleEvent\n"); int buttons = 0; int keycode = 0; bool mouse_event = false; @@ -945,15 +967,18 @@ QemuCocoaView *cocoaView; */ - (void) raiseAllKeys { - int index; const int max_index = ARRAY_SIZE(modifiers_state); - for (index = 0; index < max_index; index++) { - if (modifiers_state[index]) { - modifiers_state[index] = 0; - qemu_input_event_send_key_qcode(dcl->con, index, false); - } - } + with_iothread_lock(^{ + int index; + + for (index = 0; index < max_index; index++) { + if (modifiers_state[index]) { + modifiers_state[index] = 0; + qemu_input_event_send_key_qcode(dcl->con, index, false); + } + } + }); } @end @@ -1178,7 +1203,9 @@ QemuCocoaView *cocoaView; /* Pause the guest */ - (void)pauseQEMU:(id)sender { - qmp_stop(NULL); + with_iothread_lock(^{ + qmp_stop(NULL); + }); [sender setEnabled: NO]; [[[sender menu] itemWithTitle: @"Resume"] setEnabled: YES]; [self displayPause]; @@ -1187,7 +1214,9 @@ QemuCocoaView *cocoaView; /* Resume running the guest operating system */ - (void)resumeQEMU:(id) sender { - qmp_cont(NULL); + with_iothread_lock(^{ + qmp_cont(NULL); + }); [sender setEnabled: NO]; [[[sender menu] itemWithTitle: @"Pause"] setEnabled: YES]; [self removePause]; @@ -1215,13 +1244,17 @@ QemuCocoaView *cocoaView; /* Restarts QEMU */ - (void)restartQEMU:(id)sender { - qmp_system_reset(NULL); + with_iothread_lock(^{ + qmp_system_reset(NULL); + }); } /* Powers down QEMU */ - (void)powerDownQEMU:(id)sender { - qmp_system_powerdown(NULL); + with_iothread_lock(^{ + qmp_system_powerdown(NULL); + }); } /* Ejects the media. @@ -1237,9 +1270,11 @@ QemuCocoaView *cocoaView; return; } - Error *err = NULL; - qmp_eject(true, [drive cStringUsingEncoding: NSASCIIStringEncoding], - false, NULL, false, false, &err); + __block Error *err = NULL; + with_iothread_lock(^{ + qmp_eject(true, [drive cStringUsingEncoding: NSASCIIStringEncoding], + false, NULL, false, false, &err); + }); handleAnyDeviceErrors(err); } @@ -1271,16 +1306,18 @@ QemuCocoaView *cocoaView; return; } - Error *err = NULL; - qmp_blockdev_change_medium(true, - [drive cStringUsingEncoding: - NSASCIIStringEncoding], - false, NULL, - [file cStringUsingEncoding: - NSASCIIStringEncoding], - true, "raw", - false, 0, - &err); + __block Error *err = NULL; + with_iothread_lock(^{ + qmp_blockdev_change_medium(true, + [drive cStringUsingEncoding: + NSASCIIStringEncoding], + false, NULL, + [file cStringUsingEncoding: + NSASCIIStringEncoding], + true, "raw", + false, 0, + &err); + }); handleAnyDeviceErrors(err); } } @@ -1419,7 +1456,9 @@ QemuCocoaView *cocoaView; // get the throttle percentage throttle_pct = [sender tag]; - cpu_throttle_set(throttle_pct); + with_iothread_lock(^{ + cpu_throttle_set(throttle_pct); + }); COCOA_DEBUG("cpu throttling at %d%c\n", cpu_throttle_get_percentage(), '%'); } From patchwork Mon Mar 4 16:49:53 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 10838045 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id C08BF17E0 for ; Mon, 4 Mar 2019 16:53:59 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id AE21E2AA6E for ; Mon, 4 Mar 2019 16:53:59 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id A22162AA7A; Mon, 4 Mar 2019 16:53:59 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.7 required=2.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,MAILING_LIST_MULTI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 3B6522AA6E for ; Mon, 4 Mar 2019 16:53:59 +0000 (UTC) Received: from localhost ([127.0.0.1]:57194 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qqk-0007U9-Iu for patchwork-qemu-devel@patchwork.kernel.org; Mon, 04 Mar 2019 11:53:58 -0500 Received: from eggs.gnu.org ([209.51.188.92]:52470) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qmz-0004Mf-3m for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:05 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1h0qmy-0005hd-44 for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:05 -0500 Received: from mail-wr1-x42d.google.com ([2a00:1450:4864:20::42d]:42785) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1h0qmx-0005gr-Sv for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:04 -0500 Received: by mail-wr1-x42d.google.com with SMTP id r5so6315883wrg.9 for ; Mon, 04 Mar 2019 08:50:03 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=C52QF+raGajxS1yrkra/mHmY/s3/CCY0xtGcx1/hgZE=; b=QnTDhiAIYZYnOFXDTwtG1FLdQnXHTa5OCBcw7eN1lBEozQIonc/3zH44uBuId+g9ZV jPkQKFQgUTS1GM/UHpGgB2taTEa10eyjLWi1WERoehaV5x775WDtCAfpxCXbWXy4E0vl /F5mOTNrcWoUhCzLHGA4YaFYOMXlQXPFXsbiWhqAZuQ/sart6/LxIQkh6jV8jSCPInJ3 ffQZhjOmtqWDyb+TGA4QQ9i504xNOdQAMbb8Ks6o12BPD2MZTkNOxLCTT5ZQa6HjyxC7 e80lYvW6WHCdMfytjc72SxahvvbZGXwIgSNdI/CEKUUJQrHRRPFmzDKO44+kdCbseo6T LI/A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=C52QF+raGajxS1yrkra/mHmY/s3/CCY0xtGcx1/hgZE=; b=HROqbB8BYI9ti8rOaZ8O3T/btOyYoC6UphtZ98A+rfenuOkQh4pSJwuUtfCxjq8+u/ IFAKN5Y3NKGlBHqSMvKN24SQJQ/GS7J8EMLLCaF3VUhMz79hwjxkmHDGhWAAoFZDjuyN SQNfRQ39eRjJdhPfT1uOv33RhHTTIQ7PzlvfvByVC6pcAxH8oQg/16u57kq24vyQ4YEC moAIOnArJOOD37KSYVhePHUOdKIxlNJyXg0anwKWF/1eWVKXMTdtUXdrnfl5Oge1N/d2 m0076ZHhRNgwJsKxF/1X6L3vCXg0/HCXw0PYA6f/xHMZdAYZBnzqhpa0uD4P7Cu+ptK0 WvBA== X-Gm-Message-State: APjAAAVmA7nEQMTcPjo6ifHvXTW1HjkKYxtm3nFCsB1bv6lpO2D6b1zz TS2jgt+e2e1MPUllJUWQDFnBBScTznQ= X-Google-Smtp-Source: APXvYqxlRbHgqt9P5xo58uMY6sTUv66xdxMe3DZfubifTolPruAnpvT+Vorr9mEokFe5kyRzXDcvsw== X-Received: by 2002:adf:fb05:: with SMTP id c5mr12785509wrr.297.1551718202581; Mon, 04 Mar 2019 08:50:02 -0800 (PST) Received: from orth.archaic.org.uk (orth.archaic.org.uk. [81.2.115.148]) by smtp.gmail.com with ESMTPSA id x74sm7238018wmf.22.2019.03.04.08.50.01 for (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 04 Mar 2019 08:50:01 -0800 (PST) From: Peter Maydell To: qemu-devel@nongnu.org Date: Mon, 4 Mar 2019 16:49:53 +0000 Message-Id: <20190304164958.9362-3-peter.maydell@linaro.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20190304164958.9362-1-peter.maydell@linaro.org> References: <20190304164958.9362-1-peter.maydell@linaro.org> MIME-Version: 1.0 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:4864:20::42d Subject: [Qemu-devel] [PULL 2/7] ui/cocoa: Use the pixman image directly in switchSurface X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP Currently the switchSurface method takes a DisplaySurface. We want to change our DisplayChangeListener's dpy_gfx_switch callback to do this work asynchronously on a different thread. The caller of the switch callback will free the old DisplaySurface immediately the callback returns, so to ensure that the other thread doesn't access freed data we need to switch to using the underlying pixman image instead. The pixman image is reference counted, so we will be able to take a reference to it to avoid it vanishing too early. In this commit we only change the switchSurface method to take a pixman image, and keep the flow of control synchronous for now. Signed-off-by: Peter Maydell Reviewed-by: BALATON Zoltan Reviewed-by: Roman Bolshakov Tested-by: Roman Bolshakov Message-id: 20190225102433.22401-3-peter.maydell@linaro.org Message-id: 20190214102816.3393-3-peter.maydell@linaro.org --- ui/cocoa.m | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/ui/cocoa.m b/ui/cocoa.m index f1171c48654..a913a51a2d8 100644 --- a/ui/cocoa.m +++ b/ui/cocoa.m @@ -315,7 +315,7 @@ static void handleAnyDeviceErrors(Error * err) BOOL isAbsoluteEnabled; BOOL isMouseDeassociated; } -- (void) switchSurface:(DisplaySurface *)surface; +- (void) switchSurface:(pixman_image_t *)image; - (void) grabMouse; - (void) ungrabMouse; - (void) toggleFullScreen:(id)sender; @@ -495,12 +495,13 @@ QemuCocoaView *cocoaView; } } -- (void) switchSurface:(DisplaySurface *)surface +- (void) switchSurface:(pixman_image_t *)image { COCOA_DEBUG("QemuCocoaView: switchSurface\n"); - int w = surface_width(surface); - int h = surface_height(surface); + int w = pixman_image_get_width(image); + int h = pixman_image_get_height(image); + pixman_format_code_t image_format = pixman_image_get_format(image); /* cdx == 0 means this is our very first surface, in which case we need * to recalculate the content dimensions even if it happens to be the size * of the initial empty window. @@ -522,10 +523,10 @@ QemuCocoaView *cocoaView; CGDataProviderRelease(dataProviderRef); //sync host window color space with guests - screen.bitsPerPixel = surface_bits_per_pixel(surface); - screen.bitsPerComponent = surface_bytes_per_pixel(surface) * 2; + screen.bitsPerPixel = PIXMAN_FORMAT_BPP(image_format); + screen.bitsPerComponent = DIV_ROUND_UP(screen.bitsPerPixel, 8) * 2; - dataProviderRef = CGDataProviderCreateWithData(NULL, surface_data(surface), w * 4 * h, NULL); + dataProviderRef = CGDataProviderCreateWithData(NULL, pixman_image_get_data(image), w * 4 * h, NULL); // update windows if (isFullscreen) { @@ -1629,7 +1630,7 @@ static void cocoa_switch(DisplayChangeListener *dcl, NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; COCOA_DEBUG("qemu_cocoa: cocoa_switch\n"); - [cocoaView switchSurface:surface]; + [cocoaView switchSurface:surface->image]; [pool release]; } From patchwork Mon Mar 4 16:49:54 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 10838037 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id F09E31515 for ; Mon, 4 Mar 2019 16:51:20 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id DEF002ACBF for ; Mon, 4 Mar 2019 16:51:20 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id DD2862ACDE; Mon, 4 Mar 2019 16:51:20 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.7 required=2.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,MAILING_LIST_MULTI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 5F2632ACDD for ; Mon, 4 Mar 2019 16:51:20 +0000 (UTC) Received: from localhost ([127.0.0.1]:57165 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qoB-0005SC-Ku for patchwork-qemu-devel@patchwork.kernel.org; Mon, 04 Mar 2019 11:51:19 -0500 Received: from eggs.gnu.org ([209.51.188.92]:52481) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qn0-0004N1-4b for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:07 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1h0qmz-0005ia-6y for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:06 -0500 Received: from mail-wr1-x42a.google.com ([2a00:1450:4864:20::42a]:32889) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1h0qmz-0005hw-0M for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:05 -0500 Received: by mail-wr1-x42a.google.com with SMTP id i12so6325201wrw.0 for ; Mon, 04 Mar 2019 08:50:04 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=neXd0BAgAY98aNlWcvoddM/ZAlwCNLvn01azSi/sGsw=; b=gexdcUAPy5I26phi/WFc/bD8w4r1MfzdMXSMga3rJGU00JxfkCJGkkVO2fFHmiOXvR k7uL3wUvAx1CVB4WFPEueeYeUcOD8TrM/xX+qQSahdbo2BZdfvuG3cxvVTjkXnfhGuGl 0eEGei0ew2RjFoF5zSzb1JWWXut8qHlCknAt1ueRVWv02agvNFrKMzhluojefAB6K7Ti N5QghJkUNgeOgfBZvT0W26yxGVR7wqqtk1bxKD13OeyOc3mm0HpJ2qO/vF3LkLt0qTYL i4MQkrYBqIFLciFkLIUIHuf0R/KrXTu/SfqTf05DM/ItG6AezmXxpMbdtPy8HbPu4s+J UoLA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=neXd0BAgAY98aNlWcvoddM/ZAlwCNLvn01azSi/sGsw=; b=tgGZrzzqf+roHx+qE1lyWFT3+8B/GZ5UvzFFNjHlx0X3WARuhO0689vL1ZeKI/Tv7v Nk/7QldcZ+1v9Yy/vNK8yzaAVFchAQNfe8kgbHNYJw1N7kflzyj3l1c7qQ+ryhoCSkak 6rg0eaC3DnE4yJaxUfJkplk8S3XDxnSpP/WpR0Ke57ljxiMK7zNm591yH5p9eNM4G4HB iSSkL9gbxiJc8bMd/HXwiUBgr5TwmVISh2gLlYQwrTZiV3dHf2sEtglWWBy/PvXag643 BMsZ+dyhatYukTUSiXxwLwQD4bbVdT874Xq9M35MgcZjRyyseX7uyAc8UqLFgzGZc9W/ SOLA== X-Gm-Message-State: APjAAAVLMaVtAbcg6ss1p5n5J+rFLl0QEpix9FmWy+o/UFeWRFCjVlO7 1IUuN81qfZGe8EOp0R63H+rcdMLsvDo= X-Google-Smtp-Source: APXvYqyc4hbD4hiLK3p0xEyz235XhaWp0UoKrFHGepSJDIDcpp6ywJpC0cUjdkHyoOr67WJwgEJJ2Q== X-Received: by 2002:adf:e90b:: with SMTP id f11mr10082228wrm.36.1551718203668; Mon, 04 Mar 2019 08:50:03 -0800 (PST) Received: from orth.archaic.org.uk (orth.archaic.org.uk. [81.2.115.148]) by smtp.gmail.com with ESMTPSA id x74sm7238018wmf.22.2019.03.04.08.50.02 for (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 04 Mar 2019 08:50:02 -0800 (PST) From: Peter Maydell To: qemu-devel@nongnu.org Date: Mon, 4 Mar 2019 16:49:54 +0000 Message-Id: <20190304164958.9362-4-peter.maydell@linaro.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20190304164958.9362-1-peter.maydell@linaro.org> References: <20190304164958.9362-1-peter.maydell@linaro.org> MIME-Version: 1.0 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:4864:20::42a Subject: [Qemu-devel] [PULL 3/7] ui/cocoa: Factor out initial menu creation X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP Factor out the long code sequence in main() which creates the initial set of menus. This will make later patches which move initialization code around a bit clearer. Signed-off-by: Peter Maydell Reviewed-by: BALATON Zoltan Reviewed-by: Roman Bolshakov Tested-by: Roman Bolshakov Message-id: 20190225102433.22401-4-peter.maydell@linaro.org Message-id: 20190214102816.3393-4-peter.maydell@linaro.org --- ui/cocoa.m | 78 ++++++++++++++++++++++++++++-------------------------- 1 file changed, 41 insertions(+), 37 deletions(-) diff --git a/ui/cocoa.m b/ui/cocoa.m index a913a51a2d8..4baec0b2ff7 100644 --- a/ui/cocoa.m +++ b/ui/cocoa.m @@ -1465,43 +1465,8 @@ QemuCocoaView *cocoaView; @end - -int main (int argc, const char * argv[]) { - - gArgc = argc; - gArgv = (char **)argv; - int i; - - /* In case we don't need to display a window, let's not do that */ - for (i = 1; i < argc; i++) { - const char *opt = argv[i]; - - if (opt[0] == '-') { - /* Treat --foo the same as -foo. */ - if (opt[1] == '-') { - opt++; - } - if (!strcmp(opt, "-h") || !strcmp(opt, "-help") || - !strcmp(opt, "-vnc") || - !strcmp(opt, "-nographic") || - !strcmp(opt, "-version") || - !strcmp(opt, "-curses") || - !strcmp(opt, "-display") || - !strcmp(opt, "-qtest")) { - return qemu_main(gArgc, gArgv, *_NSGetEnviron()); - } - } - } - - NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; - - // Pull this console process up to being a fully-fledged graphical - // app with a menubar and Dock icon - ProcessSerialNumber psn = { 0, kCurrentProcess }; - TransformProcessType(&psn, kProcessTransformToForegroundApplication); - - [NSApplication sharedApplication]; - +static void create_initial_menus(void) +{ // Add menus NSMenu *menu; NSMenuItem *menuItem; @@ -1585,6 +1550,45 @@ int main (int argc, const char * argv[]) { menuItem = [[[NSMenuItem alloc] initWithTitle:@"Window" action:nil keyEquivalent:@""] autorelease]; [menuItem setSubmenu:menu]; [[NSApp mainMenu] addItem:menuItem]; +} + +int main (int argc, const char * argv[]) { + + gArgc = argc; + gArgv = (char **)argv; + int i; + + /* In case we don't need to display a window, let's not do that */ + for (i = 1; i < argc; i++) { + const char *opt = argv[i]; + + if (opt[0] == '-') { + /* Treat --foo the same as -foo. */ + if (opt[1] == '-') { + opt++; + } + if (!strcmp(opt, "-h") || !strcmp(opt, "-help") || + !strcmp(opt, "-vnc") || + !strcmp(opt, "-nographic") || + !strcmp(opt, "-version") || + !strcmp(opt, "-curses") || + !strcmp(opt, "-display") || + !strcmp(opt, "-qtest")) { + return qemu_main(gArgc, gArgv, *_NSGetEnviron()); + } + } + } + + NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; + + // Pull this console process up to being a fully-fledged graphical + // app with a menubar and Dock icon + ProcessSerialNumber psn = { 0, kCurrentProcess }; + TransformProcessType(&psn, kProcessTransformToForegroundApplication); + + [NSApplication sharedApplication]; + + create_initial_menus(); // Create an Application controller QemuCocoaAppController *appController = [[QemuCocoaAppController alloc] init]; From patchwork Mon Mar 4 16:49:55 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 10838043 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 56E771399 for ; Mon, 4 Mar 2019 16:53:59 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 423D72AA79 for ; Mon, 4 Mar 2019 16:53:59 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 350DB2AA7A; Mon, 4 Mar 2019 16:53:59 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.7 required=2.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,MAILING_LIST_MULTI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 6D9CC2AA6E for ; Mon, 4 Mar 2019 16:53:58 +0000 (UTC) Received: from localhost ([127.0.0.1]:57192 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qqj-0007TP-PP for patchwork-qemu-devel@patchwork.kernel.org; Mon, 04 Mar 2019 11:53:57 -0500 Received: from eggs.gnu.org ([209.51.188.92]:52508) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qn2-0004PI-QS for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:10 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1h0qn0-0005ja-HG for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:08 -0500 Received: from mail-wr1-x429.google.com ([2a00:1450:4864:20::429]:46994) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1h0qn0-0005is-7Y for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:06 -0500 Received: by mail-wr1-x429.google.com with SMTP id i16so6301901wrs.13 for ; Mon, 04 Mar 2019 08:50:06 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=Pxt797vQucLvBuTIV10DF3TxQ62OxtVpLOBlzSBO6oA=; b=JmqBpM22Ey2dnHokss3u9dcRGqf5ewGy1nej8uIXiNEZKmNkCNqwOCjXQrXmclLMfQ pm9ysvBvPGDvXynjFpoNmnk3sB4DsS2LpIHI4Pgn+3cSqBEtCOmtJ4JZ6+DjK0MM3pC/ ZKjsUTA86GpmluG80Ar9JKho7K3ksmnsyH7CKb30pDT8jleeInRuke3B/lT+gAMa2ip0 6XKq1HOkamAoaX1xIJzoqPFvU0n8x9Hdq5uiJSVAoVXf43JeMkBtm39jYjxLK5dFpXoJ PVdADTyTCYc4y+vxpM1MtyQeTc8ocLlAa9uJV4xxmsUUDw3uQU5ITvx9rOj3zWkvQ7HI p+gg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=Pxt797vQucLvBuTIV10DF3TxQ62OxtVpLOBlzSBO6oA=; b=afJ6VMtkivKFHsRUDC5cZFySP6Mkic60ZFQC+sSgSeTjQ8ph+ER9qMy1/TQ+UeB0y3 2UdJ0+L+W6COKaf9HUQZSbCfGib+2fuqjAqCyyV71qz6OZwQc6zyJ1j256CEAifUAZTp 1JtkaoCN11EcZ9BBCnUuDfPhjS1+O+VRrWT0AWfn0kpebNMBnR4TssUwXIhDE+o3QiNU gUR1PZOH9qhCw/iT7R84/4JoRc3mgTKNQymSCss9b9WNMt/dcH2UrpVhJiADcvwVD4r0 h3dNDmdfTUD6fMdfPIZhQs9+9p33nXTAqKjs7FsFMDKEWip39npsKfDOaoS1QElDjSCQ hezg== X-Gm-Message-State: APjAAAWY3QUMdS8+lHzuEQ+m8xJnYHSwFRNIZYr4Xybs6N+Nlhwwppjd ZaAZwb8dI/v7xMO/e50SUJj/JGbPkgE= X-Google-Smtp-Source: APXvYqwMgI7SpCyFlutxPNnmSasNhXCFpdXv4l2qr+S2/qPp/Eg/UY6gr92VvpkUGI2bJD1wjJ+0wA== X-Received: by 2002:adf:9d1d:: with SMTP id k29mr12787112wre.211.1551718204866; Mon, 04 Mar 2019 08:50:04 -0800 (PST) Received: from orth.archaic.org.uk (orth.archaic.org.uk. [81.2.115.148]) by smtp.gmail.com with ESMTPSA id x74sm7238018wmf.22.2019.03.04.08.50.03 for (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 04 Mar 2019 08:50:04 -0800 (PST) From: Peter Maydell To: qemu-devel@nongnu.org Date: Mon, 4 Mar 2019 16:49:55 +0000 Message-Id: <20190304164958.9362-5-peter.maydell@linaro.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20190304164958.9362-1-peter.maydell@linaro.org> References: <20190304164958.9362-1-peter.maydell@linaro.org> MIME-Version: 1.0 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:4864:20::429 Subject: [Qemu-devel] [PULL 4/7] ui/cocoa: Move console/device menu creation code up in file X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP Move the console/device menu creation code functions further up in the source file, next to the code which creates the initial menus. We're going to want to change the location we call these functions from in the next patch. This commit is a pure code move with no other changes. Signed-off-by: Peter Maydell Reviewed-by: BALATON Zoltan Reviewed-by: Roman Bolshakov Tested-by: Roman Bolshakov Message-id: 20190225102433.22401-5-peter.maydell@linaro.org Message-id: 20190214102816.3393-5-peter.maydell@linaro.org --- ui/cocoa.m | 184 ++++++++++++++++++++++++++--------------------------- 1 file changed, 92 insertions(+), 92 deletions(-) diff --git a/ui/cocoa.m b/ui/cocoa.m index 4baec0b2ff7..d1fc1a6aff4 100644 --- a/ui/cocoa.m +++ b/ui/cocoa.m @@ -1552,6 +1552,98 @@ static void create_initial_menus(void) [[NSApp mainMenu] addItem:menuItem]; } +/* Returns a name for a given console */ +static NSString * getConsoleName(QemuConsole * console) +{ + return [NSString stringWithFormat: @"%s", qemu_console_get_label(console)]; +} + +/* Add an entry to the View menu for each console */ +static void add_console_menu_entries(void) +{ + NSMenu *menu; + NSMenuItem *menuItem; + int index = 0; + + menu = [[[NSApp mainMenu] itemWithTitle:@"View"] submenu]; + + [menu addItem:[NSMenuItem separatorItem]]; + + while (qemu_console_lookup_by_index(index) != NULL) { + menuItem = [[[NSMenuItem alloc] initWithTitle: getConsoleName(qemu_console_lookup_by_index(index)) + action: @selector(displayConsole:) keyEquivalent: @""] autorelease]; + [menuItem setTag: index]; + [menu addItem: menuItem]; + index++; + } +} + +/* Make menu items for all removable devices. + * Each device is given an 'Eject' and 'Change' menu item. + */ +static void addRemovableDevicesMenuItems(void) +{ + NSMenu *menu; + NSMenuItem *menuItem; + BlockInfoList *currentDevice, *pointerToFree; + NSString *deviceName; + + currentDevice = qmp_query_block(NULL); + pointerToFree = currentDevice; + if(currentDevice == NULL) { + NSBeep(); + QEMU_Alert(@"Failed to query for block devices!"); + return; + } + + menu = [[[NSApp mainMenu] itemWithTitle:@"Machine"] submenu]; + + // Add a separator between related groups of menu items + [menu addItem:[NSMenuItem separatorItem]]; + + // Set the attributes to the "Removable Media" menu item + NSString *titleString = @"Removable Media"; + NSMutableAttributedString *attString=[[NSMutableAttributedString alloc] initWithString:titleString]; + NSColor *newColor = [NSColor blackColor]; + NSFontManager *fontManager = [NSFontManager sharedFontManager]; + NSFont *font = [fontManager fontWithFamily:@"Helvetica" + traits:NSBoldFontMask|NSItalicFontMask + weight:0 + size:14]; + [attString addAttribute:NSFontAttributeName value:font range:NSMakeRange(0, [titleString length])]; + [attString addAttribute:NSForegroundColorAttributeName value:newColor range:NSMakeRange(0, [titleString length])]; + [attString addAttribute:NSUnderlineStyleAttributeName value:[NSNumber numberWithInt: 1] range:NSMakeRange(0, [titleString length])]; + + // Add the "Removable Media" menu item + menuItem = [NSMenuItem new]; + [menuItem setAttributedTitle: attString]; + [menuItem setEnabled: NO]; + [menu addItem: menuItem]; + + /* Loop through all the block devices in the emulator */ + while (currentDevice) { + deviceName = [[NSString stringWithFormat: @"%s", currentDevice->value->device] retain]; + + if(currentDevice->value->removable) { + menuItem = [[NSMenuItem alloc] initWithTitle: [NSString stringWithFormat: @"Change %s...", currentDevice->value->device] + action: @selector(changeDeviceMedia:) + keyEquivalent: @""]; + [menu addItem: menuItem]; + [menuItem setRepresentedObject: deviceName]; + [menuItem autorelease]; + + menuItem = [[NSMenuItem alloc] initWithTitle: [NSString stringWithFormat: @"Eject %s", currentDevice->value->device] + action: @selector(ejectDeviceMedia:) + keyEquivalent: @""]; + [menu addItem: menuItem]; + [menuItem setRepresentedObject: deviceName]; + [menuItem autorelease]; + } + currentDevice = currentDevice->next; + } + qapi_free_BlockInfoList(pointerToFree); +} + int main (int argc, const char * argv[]) { gArgc = argc; @@ -1680,98 +1772,6 @@ static const DisplayChangeListenerOps dcl_ops = { .dpy_refresh = cocoa_refresh, }; -/* Returns a name for a given console */ -static NSString * getConsoleName(QemuConsole * console) -{ - return [NSString stringWithFormat: @"%s", qemu_console_get_label(console)]; -} - -/* Add an entry to the View menu for each console */ -static void add_console_menu_entries(void) -{ - NSMenu *menu; - NSMenuItem *menuItem; - int index = 0; - - menu = [[[NSApp mainMenu] itemWithTitle:@"View"] submenu]; - - [menu addItem:[NSMenuItem separatorItem]]; - - while (qemu_console_lookup_by_index(index) != NULL) { - menuItem = [[[NSMenuItem alloc] initWithTitle: getConsoleName(qemu_console_lookup_by_index(index)) - action: @selector(displayConsole:) keyEquivalent: @""] autorelease]; - [menuItem setTag: index]; - [menu addItem: menuItem]; - index++; - } -} - -/* Make menu items for all removable devices. - * Each device is given an 'Eject' and 'Change' menu item. - */ -static void addRemovableDevicesMenuItems(void) -{ - NSMenu *menu; - NSMenuItem *menuItem; - BlockInfoList *currentDevice, *pointerToFree; - NSString *deviceName; - - currentDevice = qmp_query_block(NULL); - pointerToFree = currentDevice; - if(currentDevice == NULL) { - NSBeep(); - QEMU_Alert(@"Failed to query for block devices!"); - return; - } - - menu = [[[NSApp mainMenu] itemWithTitle:@"Machine"] submenu]; - - // Add a separator between related groups of menu items - [menu addItem:[NSMenuItem separatorItem]]; - - // Set the attributes to the "Removable Media" menu item - NSString *titleString = @"Removable Media"; - NSMutableAttributedString *attString=[[NSMutableAttributedString alloc] initWithString:titleString]; - NSColor *newColor = [NSColor blackColor]; - NSFontManager *fontManager = [NSFontManager sharedFontManager]; - NSFont *font = [fontManager fontWithFamily:@"Helvetica" - traits:NSBoldFontMask|NSItalicFontMask - weight:0 - size:14]; - [attString addAttribute:NSFontAttributeName value:font range:NSMakeRange(0, [titleString length])]; - [attString addAttribute:NSForegroundColorAttributeName value:newColor range:NSMakeRange(0, [titleString length])]; - [attString addAttribute:NSUnderlineStyleAttributeName value:[NSNumber numberWithInt: 1] range:NSMakeRange(0, [titleString length])]; - - // Add the "Removable Media" menu item - menuItem = [NSMenuItem new]; - [menuItem setAttributedTitle: attString]; - [menuItem setEnabled: NO]; - [menu addItem: menuItem]; - - /* Loop through all the block devices in the emulator */ - while (currentDevice) { - deviceName = [[NSString stringWithFormat: @"%s", currentDevice->value->device] retain]; - - if(currentDevice->value->removable) { - menuItem = [[NSMenuItem alloc] initWithTitle: [NSString stringWithFormat: @"Change %s...", currentDevice->value->device] - action: @selector(changeDeviceMedia:) - keyEquivalent: @""]; - [menu addItem: menuItem]; - [menuItem setRepresentedObject: deviceName]; - [menuItem autorelease]; - - menuItem = [[NSMenuItem alloc] initWithTitle: [NSString stringWithFormat: @"Eject %s", currentDevice->value->device] - action: @selector(ejectDeviceMedia:) - keyEquivalent: @""]; - [menu addItem: menuItem]; - [menuItem setRepresentedObject: deviceName]; - [menuItem autorelease]; - } - currentDevice = currentDevice->next; - } - qapi_free_BlockInfoList(pointerToFree); -} - static void cocoa_display_init(DisplayState *ds, DisplayOptions *opts) { COCOA_DEBUG("qemu_cocoa: cocoa_display_init\n"); From patchwork Mon Mar 4 16:49:56 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 10838057 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id AA80E17E0 for ; Mon, 4 Mar 2019 16:57:33 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 962BC2AB84 for ; Mon, 4 Mar 2019 16:57:33 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 8A4EB2AC0C; Mon, 4 Mar 2019 16:57:33 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.7 required=2.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,MAILING_LIST_MULTI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id EE2A12AB84 for ; Mon, 4 Mar 2019 16:57:32 +0000 (UTC) Received: from localhost ([127.0.0.1]:57253 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0quC-0001xM-8l for patchwork-qemu-devel@patchwork.kernel.org; Mon, 04 Mar 2019 11:57:32 -0500 Received: from eggs.gnu.org ([209.51.188.92]:52500) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qn2-0004P3-Hm for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:09 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1h0qn1-0005ka-G2 for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:08 -0500 Received: from mail-wr1-x42a.google.com ([2a00:1450:4864:20::42a]:36970) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1h0qn1-0005k0-6J for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:07 -0500 Received: by mail-wr1-x42a.google.com with SMTP id w6so6320563wrs.4 for ; Mon, 04 Mar 2019 08:50:07 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=gcFShq28SeXckPj3K18dzebRvmC0E8l9cqlRJnbBFbk=; b=I6Ex5jd7Kx5Hj8d3+R/598uMfNWKBqpUWemACPwp65E5SG2vbv1GSzQ+WGV0y3rSti 63TqU8A3pJZDFOG4/iQJ/5SV6ooLanM4gFPBARX4wq7i8vn2oKGTZwcbhD5CYiHOWCBq F4QgUv+EbX/r5DvJaiJA5O8vIspUaDcwqJ54OCBBFx8jbUQcE3DmKvX4S8h3Imxc/Bc0 cqTn6GJ35aX2wjkRdv9X5J+q6WSarNNIp3lYWdcr0bRZNwDqzW4uPSej29eP5d0mZFbp FU1CeuFzy6DaAEIbi+386vZhcAV1C4VVfWLV5d+4gTMIr81vKseStD/CVbon9Vzz/VKR IGBQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=gcFShq28SeXckPj3K18dzebRvmC0E8l9cqlRJnbBFbk=; b=dHP6xDSCb3QDReAXOlh1KMkSGd88ef04XSMXKvhPldhYrRVJwzu60ewCbkxERh5A7Q VYNX57lIQE4iKJ33l+xJdL6wUDtflt9lBxUcZhkkK8CvhNhFtavdSDKKzMwylnV+P0wQ rzz8yAWQUBgOHG+73rtKklgImUKjE3+mu4KgShQoSwEu8Wd8S8QJBv0zSAB/Nj1e+YBm kozao5wEuNNygkW0KBR9mvzClnHh6lE/3ChVkjCTfQJ5e4ab5QcbYreilU4LcwupbWhE 93aeKqAxAduEd7jSxdoi5lEYgYtpZ6GS2CvtfP1KaQR5pwb2hvBBAVtQnMZtfJNCjBfa gnnw== X-Gm-Message-State: APjAAAWSBD7V70ncuLUpPeNxDG6yQe4A/hSOXykcpOQfuO4E5ERneM+1 VYP7dvvIJjTiCqdq/j0srDSkam9Cm+I= X-Google-Smtp-Source: APXvYqwPOslKa0XJL72XRZNvNkbOU/m5SYWsvpb2SaXGwooJkeYF8Cooth2xtlaEqfn0LO0M180ydQ== X-Received: by 2002:adf:9e0c:: with SMTP id u12mr12951608wre.216.1551718205949; Mon, 04 Mar 2019 08:50:05 -0800 (PST) Received: from orth.archaic.org.uk (orth.archaic.org.uk. [81.2.115.148]) by smtp.gmail.com with ESMTPSA id x74sm7238018wmf.22.2019.03.04.08.50.04 for (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 04 Mar 2019 08:50:05 -0800 (PST) From: Peter Maydell To: qemu-devel@nongnu.org Date: Mon, 4 Mar 2019 16:49:56 +0000 Message-Id: <20190304164958.9362-6-peter.maydell@linaro.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20190304164958.9362-1-peter.maydell@linaro.org> References: <20190304164958.9362-1-peter.maydell@linaro.org> MIME-Version: 1.0 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:4864:20::42a Subject: [Qemu-devel] [PULL 5/7] ui/cocoa: Don't call NSApp sendEvent directly from handleEvent X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP Currently the handleEvent method will directly call the NSApp sendEvent method for any events that we want to let OSX deal with. When we rearrange the event handling code, the way that we say "let OSX have this event" is going to change. Prepare for that by refactoring so that handleEvent returns a flag indicating whether it consumed the event. Suggested-by: BALATON Zoltan Signed-off-by: Peter Maydell Reviewed-by: BALATON Zoltan Reviewed-by: Roman Bolshakov Tested-by: Roman Bolshakov Message-id: 20190225102433.22401-6-peter.maydell@linaro.org Message-id: 20190214102816.3393-6-peter.maydell@linaro.org --- ui/cocoa.m | 49 ++++++++++++++++++++++++++++++++++--------------- 1 file changed, 34 insertions(+), 15 deletions(-) diff --git a/ui/cocoa.m b/ui/cocoa.m index d1fc1a6aff4..1b54d42aba6 100644 --- a/ui/cocoa.m +++ b/ui/cocoa.m @@ -129,8 +129,9 @@ bool stretch_video; NSTextField *pauseLabel; NSArray * supportedImageFileTypes; -// Utility function to run specified code block with iothread lock held +// Utility functions to run specified code block with iothread lock held typedef void (^CodeBlock)(void); +typedef bool (^BoolCodeBlock)(void); static void with_iothread_lock(CodeBlock block) { @@ -144,6 +145,21 @@ static void with_iothread_lock(CodeBlock block) } } +static bool bool_with_iothread_lock(BoolCodeBlock block) +{ + bool locked = qemu_mutex_iothread_locked(); + bool val; + + if (!locked) { + qemu_mutex_lock_iothread(); + } + val = block(); + if (!locked) { + qemu_mutex_unlock_iothread(); + } + return val; +} + // Mac to QKeyCode conversion const int mac_to_qkeycode_map[] = { [kVK_ANSI_A] = Q_KEY_CODE_A, @@ -320,8 +336,8 @@ static void handleAnyDeviceErrors(Error * err) - (void) ungrabMouse; - (void) toggleFullScreen:(id)sender; - (void) handleMonitorInput:(NSEvent *)event; -- (void) handleEvent:(NSEvent *)event; -- (void) handleEventLocked:(NSEvent *)event; +- (bool) handleEvent:(NSEvent *)event; +- (bool) handleEventLocked:(NSEvent *)event; - (void) setAbsoluteEnabled:(BOOL)tIsAbsoluteEnabled; /* The state surrounding mouse grabbing is potentially confusing. * isAbsoluteEnabled tracks qemu_input_is_absolute() [ie "is the emulated @@ -664,15 +680,16 @@ QemuCocoaView *cocoaView; } } -- (void) handleEvent:(NSEvent *)event +- (bool) handleEvent:(NSEvent *)event { - with_iothread_lock(^{ - [self handleEventLocked:event]; + return bool_with_iothread_lock(^{ + return [self handleEventLocked:event]; }); } -- (void) handleEventLocked:(NSEvent *)event +- (bool) handleEventLocked:(NSEvent *)event { + /* Return true if we handled the event, false if it should be given to OSX */ COCOA_DEBUG("QemuCocoaView: handleEvent\n"); int buttons = 0; int keycode = 0; @@ -743,8 +760,7 @@ QemuCocoaView *cocoaView; if (keycode == Q_KEY_CODE_F) { switched_to_fullscreen = true; } - [NSApp sendEvent:event]; - return; + return false; } // default @@ -759,12 +775,12 @@ QemuCocoaView *cocoaView; // enable graphic console case '1' ... '9': console_select(key - '0' - 1); /* ascii math */ - return; + return true; // release the mouse grab case 'g': [self ungrabMouse]; - return; + return true; } } } @@ -781,7 +797,7 @@ QemuCocoaView *cocoaView; // don't pass the guest a spurious key-up if we treated this // command-key combo as a host UI action if (!isMouseGrabbed && ([event modifierFlags] & NSEventModifierFlagCommand)) { - return; + return true; } if (qemu_console_is_graphic(NULL)) { @@ -875,7 +891,7 @@ QemuCocoaView *cocoaView; mouse_event = false; break; default: - [NSApp sendEvent:event]; + return false; } if (mouse_event) { @@ -911,10 +927,11 @@ QemuCocoaView *cocoaView; qemu_input_queue_rel(dcl->con, INPUT_AXIS_Y, (int)[event deltaY]); } } else { - [NSApp sendEvent:event]; + return false; } qemu_input_event_sync(); } + return true; } - (void) grabMouse @@ -1753,7 +1770,9 @@ static void cocoa_refresh(DisplayChangeListener *dcl) event = [NSApp nextEventMatchingMask:NSEventMaskAny untilDate:distantPast inMode: NSDefaultRunLoopMode dequeue:YES]; if (event != nil) { - [cocoaView handleEvent:event]; + if (![cocoaView handleEvent:event]) { + [NSApp sendEvent:event]; + } } } while(event != nil); [pool release]; From patchwork Mon Mar 4 16:49:57 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 10838049 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id 24C171399 for ; Mon, 4 Mar 2019 16:56:26 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 119672AB00 for ; Mon, 4 Mar 2019 16:56:26 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 05F632AB3B; Mon, 4 Mar 2019 16:56:26 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.7 required=2.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,MAILING_LIST_MULTI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 7E9882AB00 for ; Mon, 4 Mar 2019 16:56:25 +0000 (UTC) Received: from localhost ([127.0.0.1]:57245 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qt6-00011S-Ib for patchwork-qemu-devel@patchwork.kernel.org; Mon, 04 Mar 2019 11:56:24 -0500 Received: from eggs.gnu.org ([209.51.188.92]:52520) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qn4-0004Qb-2T for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:10 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1h0qn2-0005lF-8G for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:10 -0500 Received: from mail-wr1-x42d.google.com ([2a00:1450:4864:20::42d]:40940) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1h0qn2-0005ke-19 for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:08 -0500 Received: by mail-wr1-x42d.google.com with SMTP id q1so6331569wrp.7 for ; Mon, 04 Mar 2019 08:50:07 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=n6lY7pkDMpwdLdV8Ya73A0/SHkQC1GkvAVdq2F4IskM=; b=r3XckG6TI/fPx2NjEMrQCvIfnrNEeSl8b2ovQWT8Tlnvq9kkr6C2+yddX7hKPWzjuJ efVr3QaNWOxx8wm5fmUASUvwVz5t9gsXXtdF8KfasdSWPgJ3B5dR0l6ZyVl5U4UG/E8I 7j7l0IuAAMj0SDA6lVPbhu+PuGkp8GCEdFPMTbwuz+IthHAA8N+ePO6e0zqBjbtGPVs+ v+2MulJ7Vcg7HCSK/d8oJappoEtmq448THONZphg6BE/UdgpppfAGiwqwPPJ+1oIrrsx Q8D1CQtirWu4p4Z71lum8IMaMjyKx/ahvTuGgT/PWgZm0xANYgkW6fcW2+gqdFR307Xg X/bQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=n6lY7pkDMpwdLdV8Ya73A0/SHkQC1GkvAVdq2F4IskM=; b=U4KcOn6/1rioaNsJv2EBWimAgNz+J0daCyvWIDSOpFJ/oxMEbvy7v0OPfiYojACtW6 yFhYCnwpKMjJ2mISLyVNj6fhn/+95QfXnJRxvRBXgAERyAFaJXAG91oJ20HirFyVERjw /f60dkyfyXrIgoyxcTVX02bPzbS+aHEHFu6/RyxKNZRng8DXC1ExJ+YVJzteTTf1EZR7 W46LDVwu4rzN6Vp6d02z4NC0eLj+Psl9fpB8RvU04/S+ohxYeZqgzFAckE4ymupsEVwA zmZE8x1C1Y0U2QUlH78t/wpc4bHgnzEdusX1kWUpSObvDLsZZzp+aUJ1hnKme9UelvT3 rxSw== X-Gm-Message-State: APjAAAUiuv1CvFdopdonVsusdYHPBrd/JmCuG8xDxBgLyO2KrisK/MDh XqgsXJXLRFDZX6sIVqXijG8A65jLNdI= X-Google-Smtp-Source: APXvYqxIhcBp5ahHM51IBzm7Al6VCJ/m4YEs4JuBM+WV9yn+u66y53uYD6PnunVF+gTvyI4MOUXEyw== X-Received: by 2002:adf:b741:: with SMTP id n1mr12833962wre.287.1551718206884; Mon, 04 Mar 2019 08:50:06 -0800 (PST) Received: from orth.archaic.org.uk (orth.archaic.org.uk. [81.2.115.148]) by smtp.gmail.com with ESMTPSA id x74sm7238018wmf.22.2019.03.04.08.50.05 for (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 04 Mar 2019 08:50:06 -0800 (PST) From: Peter Maydell To: qemu-devel@nongnu.org Date: Mon, 4 Mar 2019 16:49:57 +0000 Message-Id: <20190304164958.9362-7-peter.maydell@linaro.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20190304164958.9362-1-peter.maydell@linaro.org> References: <20190304164958.9362-1-peter.maydell@linaro.org> MIME-Version: 1.0 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:4864:20::42d Subject: [Qemu-devel] [PULL 6/7] ui/cocoa: Subclass NSApplication so we can implement sendEvent X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP When we switch away from our custom event handling, we still want to be able to have first go at any events our application receives, because in full-screen mode we want to send key events to the guest, even if they would be menu item activation events. There are several ways we could do that, but one simple approach is to subclass NSApplication so we can implement a custom sendEvent method. Do that, but for the moment have our sendEvent just invoke the superclass method. Signed-off-by: Peter Maydell Reviewed-by: BALATON Zoltan Reviewed-by: Roman Bolshakov Tested-by: Roman Bolshakov Message-id: 20190225102433.22401-7-peter.maydell@linaro.org Message-id: 20190214102816.3393-7-peter.maydell@linaro.org --- ui/cocoa.m | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/ui/cocoa.m b/ui/cocoa.m index 1b54d42aba6..00e3db69c91 100644 --- a/ui/cocoa.m +++ b/ui/cocoa.m @@ -1482,6 +1482,17 @@ QemuCocoaView *cocoaView; @end +@interface QemuApplication : NSApplication +@end + +@implementation QemuApplication +- (void)sendEvent:(NSEvent *)event +{ + COCOA_DEBUG("QemuApplication: sendEvent\n"); + [super sendEvent: event]; +} +@end + static void create_initial_menus(void) { // Add menus @@ -1695,7 +1706,7 @@ int main (int argc, const char * argv[]) { ProcessSerialNumber psn = { 0, kCurrentProcess }; TransformProcessType(&psn, kProcessTransformToForegroundApplication); - [NSApplication sharedApplication]; + [QemuApplication sharedApplication]; create_initial_menus(); From patchwork Mon Mar 4 16:49:58 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Peter Maydell X-Patchwork-Id: 10838075 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork-2.web.codeaurora.org (Postfix) with ESMTP id D53E41399 for ; Mon, 4 Mar 2019 16:59:56 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id BE6AA2AB4C for ; Mon, 4 Mar 2019 16:59:56 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id B211D2AB78; Mon, 4 Mar 2019 16:59:56 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-2.7 required=2.0 tests=BAYES_00,DKIM_INVALID, DKIM_SIGNED,MAILING_LIST_MULTI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id CAF6A2AB4C for ; Mon, 4 Mar 2019 16:59:55 +0000 (UTC) Received: from localhost ([127.0.0.1]:57283 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qwV-00046O-5p for patchwork-qemu-devel@patchwork.kernel.org; Mon, 04 Mar 2019 11:59:55 -0500 Received: from eggs.gnu.org ([209.51.188.92]:52535) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1h0qn5-0004SS-UJ for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:13 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1h0qn3-0005ms-Tu for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:11 -0500 Received: from mail-wr1-x42e.google.com ([2a00:1450:4864:20::42e]:34816) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16) (Exim 4.71) (envelope-from ) id 1h0qn3-0005mG-Jr for qemu-devel@nongnu.org; Mon, 04 Mar 2019 11:50:09 -0500 Received: by mail-wr1-x42e.google.com with SMTP id t18so6334172wrx.2 for ; Mon, 04 Mar 2019 08:50:09 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=from:to:subject:date:message-id:in-reply-to:references:mime-version :content-transfer-encoding; bh=iEZ8xWsGFQnnfCPhhe+VWXCcfkJ4AqfX00aEDhMQjI4=; b=NjvJ4usM2LUw35CvtXW3ZwL6ugl2Q1voI3IfoAofe7lsnv5c5QfZeQC8ibKjeEzjru cWJPqQLbOSrSOqEdHhx8Z+b9z38wPrSroeUraR2CBhM7MmGEklrlVy48EPHEs4wG02Yh B4vR33fRYmsJ/xSdTh1PUDZN6gatX5rE9uJ1+v2JbIWisI+MRuxa5G4AllVQFuuBJ7aG 5msaxSOVxYprAAD4OyjhSp3QUiYjXgjXTDFPtUN62u89QH2rc+fguRynfx9t2e9dMV7v MdVURxet6SQNStJrhnJ2+p56QLF2Q4dUBX7ksXC/Gj82tKMdvXJYkM2ya0+429Eko2Uz SVuw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to :references:mime-version:content-transfer-encoding; bh=iEZ8xWsGFQnnfCPhhe+VWXCcfkJ4AqfX00aEDhMQjI4=; b=UjwHuqrQLgFgF4PTc9UZhgq3GilBzt34fftgULAILMdfZWNqBtEt1b9tTEuiF41pM6 5sH/WVwsaTxd5L+ZGfpbeUBdB059K3IPEr03dUzY53h/SGZimAn4nvFuDaiZd74RfJg9 i9Lpyi0Bwcn/62lYoRaGKsVtACEBdBKUx03c/i0r+NT4e2RVwqwkj3NAgPiGwBbMuLyh 9xEHtRZxj7mfPdbjts0Zum8+uW7GPtIRithjogobTNY1fvTaVX1V7CTAxbM4IhTHIOvP C8WF7BZG3gcZZhb0lNAHapz1iBfO/uRPZwERxi6UUxuQTDY4qrm7fnqb/ihjQsCQzFM6 b5Lg== X-Gm-Message-State: APjAAAWFs+A/FJM3JCnVugH5/LXiFyCu8kD+z8CZjZnkijeoCrT4osK9 UXh1AS70GXK0O81JPS7/8Msry30QrgY= X-Google-Smtp-Source: APXvYqxU1Q9BuJELtpYp+vv+4eRAtJeF7VkuvBcBxryViihcSrS16C0yE+01nQ9jHjnrVhCDr56fow== X-Received: by 2002:adf:e90b:: with SMTP id f11mr10082492wrm.36.1551718208215; Mon, 04 Mar 2019 08:50:08 -0800 (PST) Received: from orth.archaic.org.uk (orth.archaic.org.uk. [81.2.115.148]) by smtp.gmail.com with ESMTPSA id x74sm7238018wmf.22.2019.03.04.08.50.06 for (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Mon, 04 Mar 2019 08:50:07 -0800 (PST) From: Peter Maydell To: qemu-devel@nongnu.org Date: Mon, 4 Mar 2019 16:49:58 +0000 Message-Id: <20190304164958.9362-8-peter.maydell@linaro.org> X-Mailer: git-send-email 2.20.1 In-Reply-To: <20190304164958.9362-1-peter.maydell@linaro.org> References: <20190304164958.9362-1-peter.maydell@linaro.org> MIME-Version: 1.0 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a00:1450:4864:20::42e Subject: [Qemu-devel] [PULL 7/7] ui/cocoa: Perform UI operations only on the main thread X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP The OSX Mojave release is more picky about enforcing the Cocoa API restriction that only the main thread may perform UI calls. To accommodate this we need to restructure the Cocoa code: * the special OSX main() creates a second thread and uses that to call the vl.c qemu_main(); the original main thread goes into the OSX event loop * the refresh, switch and update callbacks asynchronously tell the main thread to do the necessary work * the refresh callback no longer does the "get events from the UI event queue and handle them" loop, since we now use the stock OSX event loop. Instead our NSApplication sendEvent method will either deal with them or pass them on to OSX All these things have to be changed in one commit, to avoid breaking bisection. Note that since we use dispatch_get_main_queue(), this bumps our minimum version requirement to OSX 10.10 Yosemite (released in 2014, unsupported by Apple since 2017). Signed-off-by: Peter Maydell Reviewed-by: Roman Bolshakov Tested-by: Roman Bolshakov Message-id: 20190225102433.22401-8-peter.maydell@linaro.org Message-id: 20190214102816.3393-8-peter.maydell@linaro.org --- ui/cocoa.m | 195 +++++++++++++++++++++++++++++++---------------------- 1 file changed, 116 insertions(+), 79 deletions(-) diff --git a/ui/cocoa.m b/ui/cocoa.m index 00e3db69c91..420b2411c10 100644 --- a/ui/cocoa.m +++ b/ui/cocoa.m @@ -129,6 +129,9 @@ bool stretch_video; NSTextField *pauseLabel; NSArray * supportedImageFileTypes; +static QemuSemaphore display_init_sem; +static QemuSemaphore app_started_sem; + // Utility functions to run specified code block with iothread lock held typedef void (^CodeBlock)(void); typedef bool (^BoolCodeBlock)(void); @@ -325,6 +328,7 @@ static void handleAnyDeviceErrors(Error * err) NSWindow *fullScreenWindow; float cx,cy,cw,ch,cdx,cdy; CGDataProviderRef dataProviderRef; + pixman_image_t *pixman_image; BOOL modifiers_state[256]; BOOL isMouseGrabbed; BOOL isFullscreen; @@ -383,8 +387,10 @@ QemuCocoaView *cocoaView; { COCOA_DEBUG("QemuCocoaView: dealloc\n"); - if (dataProviderRef) + if (dataProviderRef) { CGDataProviderRelease(dataProviderRef); + pixman_image_unref(pixman_image); + } [super dealloc]; } @@ -535,13 +541,16 @@ QemuCocoaView *cocoaView; } // update screenBuffer - if (dataProviderRef) + if (dataProviderRef) { CGDataProviderRelease(dataProviderRef); + pixman_image_unref(pixman_image); + } //sync host window color space with guests screen.bitsPerPixel = PIXMAN_FORMAT_BPP(image_format); screen.bitsPerComponent = DIV_ROUND_UP(screen.bitsPerPixel, 8) * 2; + pixman_image = image; dataProviderRef = CGDataProviderCreateWithData(NULL, pixman_image_get_data(image), w * 4 * h, NULL); // update windows @@ -1013,7 +1022,6 @@ QemuCocoaView *cocoaView; #endif { } -- (void)startEmulationWithArgc:(int)argc argv:(char**)argv; - (void)doToggleFullScreen:(id)sender; - (void)toggleFullScreen:(id)sender; - (void)showQEMUDoc:(id)sender; @@ -1101,8 +1109,8 @@ QemuCocoaView *cocoaView; - (void)applicationDidFinishLaunching: (NSNotification *) note { COCOA_DEBUG("QemuCocoaAppController: applicationDidFinishLaunching\n"); - // launch QEMU, with the global args - [self startEmulationWithArgc:gArgc argv:(char **)gArgv]; + /* Tell cocoa_display_init to proceed */ + qemu_sem_post(&app_started_sem); } - (void)applicationWillTerminate:(NSNotification *)aNotification @@ -1145,15 +1153,6 @@ QemuCocoaView *cocoaView; [cocoaView raiseAllKeys]; } -- (void)startEmulationWithArgc:(int)argc argv:(char**)argv -{ - COCOA_DEBUG("QemuCocoaAppController: startEmulationWithArgc\n"); - - int status; - status = qemu_main(argc, argv, *_NSGetEnviron()); - exit(status); -} - /* We abstract the method called by the Enter Fullscreen menu item * because Mac OS 10.7 and higher disables it. This is because of the * menu item's old selector's name toggleFullScreen: @@ -1489,7 +1488,9 @@ QemuCocoaView *cocoaView; - (void)sendEvent:(NSEvent *)event { COCOA_DEBUG("QemuApplication: sendEvent\n"); - [super sendEvent: event]; + if (![cocoaView handleEvent:event]) { + [super sendEvent: event]; + } } @end @@ -1672,32 +1673,59 @@ static void addRemovableDevicesMenuItems(void) qapi_free_BlockInfoList(pointerToFree); } -int main (int argc, const char * argv[]) { +/* + * The startup process for the OSX/Cocoa UI is complicated, because + * OSX insists that the UI runs on the initial main thread, and so we + * need to start a second thread which runs the vl.c qemu_main(): + * + * Initial thread: 2nd thread: + * in main(): + * create qemu-main thread + * wait on display_init semaphore + * call qemu_main() + * ... + * in cocoa_display_init(): + * post the display_init semaphore + * wait on app_started semaphore + * create application, menus, etc + * enter OSX run loop + * in applicationDidFinishLaunching: + * post app_started semaphore + * tell main thread to fullscreen if needed + * [...] + * run qemu main-loop + * + * We do this in two stages so that we don't do the creation of the + * GUI application menus and so on for command line options like --help + * where we want to just print text to stdout and exit immediately. + */ +static void *call_qemu_main(void *opaque) +{ + int status; + + COCOA_DEBUG("Second thread: calling qemu_main()\n"); + status = qemu_main(gArgc, gArgv, *_NSGetEnviron()); + COCOA_DEBUG("Second thread: qemu_main() returned, exiting\n"); + exit(status); +} + +int main (int argc, const char * argv[]) { + QemuThread thread; + + COCOA_DEBUG("Entered main()\n"); gArgc = argc; gArgv = (char **)argv; - int i; - /* In case we don't need to display a window, let's not do that */ - for (i = 1; i < argc; i++) { - const char *opt = argv[i]; + qemu_sem_init(&display_init_sem, 0); + qemu_sem_init(&app_started_sem, 0); - if (opt[0] == '-') { - /* Treat --foo the same as -foo. */ - if (opt[1] == '-') { - opt++; - } - if (!strcmp(opt, "-h") || !strcmp(opt, "-help") || - !strcmp(opt, "-vnc") || - !strcmp(opt, "-nographic") || - !strcmp(opt, "-version") || - !strcmp(opt, "-curses") || - !strcmp(opt, "-display") || - !strcmp(opt, "-qtest")) { - return qemu_main(gArgc, gArgv, *_NSGetEnviron()); - } - } - } + qemu_thread_create(&thread, "qemu_main", call_qemu_main, + NULL, QEMU_THREAD_DETACHED); + + COCOA_DEBUG("Main thread: waiting for display_init_sem\n"); + qemu_sem_wait(&display_init_sem); + COCOA_DEBUG("Main thread: initializing app\n"); NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; @@ -1710,12 +1738,24 @@ int main (int argc, const char * argv[]) { create_initial_menus(); + /* + * Create the menu entries which depend on QEMU state (for consoles + * and removeable devices). These make calls back into QEMU functions, + * which is OK because at this point we know that the second thread + * holds the iothread lock and is synchronously waiting for us to + * finish. + */ + add_console_menu_entries(); + addRemovableDevicesMenuItems(); + // Create an Application controller QemuCocoaAppController *appController = [[QemuCocoaAppController alloc] init]; [NSApp setDelegate:appController]; // Start the main event loop + COCOA_DEBUG("Main thread: entering OSX run loop\n"); [NSApp run]; + COCOA_DEBUG("Main thread: left OSX run loop, exiting\n"); [appController release]; [pool release]; @@ -1733,17 +1773,19 @@ static void cocoa_update(DisplayChangeListener *dcl, COCOA_DEBUG("qemu_cocoa: cocoa_update\n"); - NSRect rect; - if ([cocoaView cdx] == 1.0) { - rect = NSMakeRect(x, [cocoaView gscreen].height - y - h, w, h); - } else { - rect = NSMakeRect( - x * [cocoaView cdx], - ([cocoaView gscreen].height - y - h) * [cocoaView cdy], - w * [cocoaView cdx], - h * [cocoaView cdy]); - } - [cocoaView setNeedsDisplayInRect:rect]; + dispatch_async(dispatch_get_main_queue(), ^{ + NSRect rect; + if ([cocoaView cdx] == 1.0) { + rect = NSMakeRect(x, [cocoaView gscreen].height - y - h, w, h); + } else { + rect = NSMakeRect( + x * [cocoaView cdx], + ([cocoaView gscreen].height - y - h) * [cocoaView cdy], + w * [cocoaView cdx], + h * [cocoaView cdy]); + } + [cocoaView setNeedsDisplayInRect:rect]; + }); [pool release]; } @@ -1752,9 +1794,19 @@ static void cocoa_switch(DisplayChangeListener *dcl, DisplaySurface *surface) { NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; + pixman_image_t *image = surface->image; COCOA_DEBUG("qemu_cocoa: cocoa_switch\n"); - [cocoaView switchSurface:surface->image]; + + // The DisplaySurface will be freed as soon as this callback returns. + // We take a reference to the underlying pixman image here so it does + // not disappear from under our feet; the switchSurface method will + // deref the old image when it is done with it. + pixman_image_ref(image); + + dispatch_async(dispatch_get_main_queue(), ^{ + [cocoaView switchSurface:image]; + }); [pool release]; } @@ -1766,26 +1818,15 @@ static void cocoa_refresh(DisplayChangeListener *dcl) graphic_hw_update(NULL); if (qemu_input_is_absolute()) { - if (![cocoaView isAbsoluteEnabled]) { - if ([cocoaView isMouseGrabbed]) { - [cocoaView ungrabMouse]; + dispatch_async(dispatch_get_main_queue(), ^{ + if (![cocoaView isAbsoluteEnabled]) { + if ([cocoaView isMouseGrabbed]) { + [cocoaView ungrabMouse]; + } } - } - [cocoaView setAbsoluteEnabled:YES]; + [cocoaView setAbsoluteEnabled:YES]; + }); } - - NSDate *distantPast; - NSEvent *event; - distantPast = [NSDate distantPast]; - do { - event = [NSApp nextEventMatchingMask:NSEventMaskAny untilDate:distantPast - inMode: NSDefaultRunLoopMode dequeue:YES]; - if (event != nil) { - if (![cocoaView handleEvent:event]) { - [NSApp sendEvent:event]; - } - } - } while(event != nil); [pool release]; } @@ -1806,10 +1847,17 @@ static void cocoa_display_init(DisplayState *ds, DisplayOptions *opts) { COCOA_DEBUG("qemu_cocoa: cocoa_display_init\n"); + /* Tell main thread to go ahead and create the app and enter the run loop */ + qemu_sem_post(&display_init_sem); + qemu_sem_wait(&app_started_sem); + COCOA_DEBUG("cocoa_display_init: app start completed\n"); + /* if fullscreen mode is to be used */ if (opts->has_full_screen && opts->full_screen) { - [NSApp activateIgnoringOtherApps: YES]; - [(QemuCocoaAppController *)[[NSApplication sharedApplication] delegate] toggleFullScreen: nil]; + dispatch_async(dispatch_get_main_queue(), ^{ + [NSApp activateIgnoringOtherApps: YES]; + [(QemuCocoaAppController *)[[NSApplication sharedApplication] delegate] toggleFullScreen: nil]; + }); } dcl = g_malloc0(sizeof(DisplayChangeListener)); @@ -1820,17 +1868,6 @@ static void cocoa_display_init(DisplayState *ds, DisplayOptions *opts) // register cleanup function atexit(cocoa_cleanup); - - /* At this point QEMU has created all the consoles, so we can add View - * menu entries for them. - */ - add_console_menu_entries(); - - /* Give all removable devices a menu item. - * Has to be called after QEMU has started to - * find out what removable devices it has. - */ - addRemovableDevicesMenuItems(); } static QemuDisplay qemu_display_cocoa = {