qemu-devel.nongnu.org archive mirror
 help / color / mirror / Atom feed
* [PULL 00/52] UI patches
@ 2023-09-04 11:51 marcandre.lureau
  2023-09-04 11:51 ` [PULL 01/52] ui: remove qemu_pixman_color() helper marcandre.lureau
                   ` (52 more replies)
  0 siblings, 53 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:51 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau

From: Marc-André Lureau <marcandre.lureau@redhat.com>

The following changes since commit 17780edd81d27fcfdb7a802efc870a99788bd2fc:

  Merge tag 'quick-fix-pull-request' of https://gitlab.com/bsdimp/qemu into staging (2023-08-31 10:06:29 -0400)

are available in the Git repository at:

  https://gitlab.com/marcandre.lureau/qemu.git tags/ui-pull-request

for you to fetch changes up to e38f4e976dd40c985bfe84230a627de9a108c9d3:

  ui/gtk: fix leaks found wtih fuzzing (2023-09-04 15:37:50 +0400)

----------------------------------------------------------------
UI patch queue

- misc fixes and improvement
- cleanups and refactoring in ui/vc code

----------------------------------------------------------------

Bilal Elmoussaoui (2):
  ui/dbus: Properly dispose touch/mouse dbus objects
  ui/dbus: implement damage regions for GL

Dmitry Frolov (1):
  ui/gtk: fix leaks found wtih fuzzing

Guoyi Tu (2):
  ui/vdagent: call vdagent_disconnect() when agent connection is lost
  ui/vdagent: Unregister input handler of mouse during finalization

Marc-André Lureau (44):
  ui: remove qemu_pixman_color() helper
  ui: remove qemu_pixman_linebuf_copy()
  ui/qmp: move screendump to ui-qmp-cmds.c
  ui/vc: replace vc_chr_write() with generic qemu_chr_write()
  ui/vc: drop have_text
  ui/console: console_select() regardless of have_gfx
  ui/console: call dpy_gfx_update() regardless of have_gfx
  ui/console: drop have_gfx
  ui/console: get the DisplayState from new_console()
  ui/console: new_console() cannot fail
  ui/vc: VC always has a DisplayState now
  ui/vc: move VCChardev declaration at the top
  ui/vc: replace variable with static text attributes default
  ui/vc: fold text_update_xy()
  ui/vc: pass VCCharDev to VC-specific functions
  ui/vc: move VCCharDev specific fields out of QemuConsole
  ui/console: use OBJECT_DEFINE_TYPE for QemuConsole
  ui/console: change new_console() to use object initialization
  ui/console: introduce different console objects
  ui/console: instantiate a specific console type
  ui/console: register the console from qemu_console_init()
  ui/console: remove new_console()
  ui/console: specialize console_lookup_unused()
  ui/console: update the head from unused QemuConsole
  ui/console: allocate ui_timer in QemuConsole
  ui/vc: move cursor_timer initialization to QemuTextConsole class
  ui/console: free more QemuConsole resources
  ui/vc: move text fields to QemuTextConsole
  ui/console: move graphic fields to QemuGraphicConsole
  ui/vc: fold text_console_do_init() in vc_chr_open()
  ui/vc: move some text console initialization to qom handlers
  ui/console: simplify getting active_console size
  ui/console: remove need for g_width/g_height
  ui/vc: use common text console surface creation
  ui/console: declare console types in console.h
  ui/console: use QEMU_PIXMAN_COLOR helpers
  ui/console: rename vga_ functions with qemu_console_
  ui/console: assert(surface) where appropriate
  ui/console: fold text_console_update_cursor_timer
  ui/vc: skip text console resize when possible
  ui/console: minor stylistic changes
  ui/vc: move text console invalidate in helper
  ui/vc: do not parse VC-specific options in Spice and GTK
  ui/vc: change the argument for QemuTextConsole

Peter Maydell (2):
  ui/spice-display: Avoid dynamic stack allocation
  ui/vnc-enc-hextile: Use static rather than dynamic length stack array

Philippe Mathieu-Daudé (1):
  ui/vnc-enc-tight: Avoid dynamic stack allocation

 qapi/char.json                |    4 +
 include/chardev/char.h        |    3 -
 include/ui/console.h          |   34 +-
 include/ui/qemu-pixman.h      |    9 +-
 ui/vnc-enc-hextile-template.h |    8 +-
 ui/console.c                  | 1125 ++++++++++++++-------------------
 ui/dbus-console.c             |    2 +
 ui/dbus-listener.c            |   32 +-
 ui/gtk.c                      |    6 +-
 ui/qemu-pixman.c              |   19 -
 ui/sdl2-input.c               |    7 +-
 ui/sdl2.c                     |    5 +-
 ui/spice-app.c                |    7 +-
 ui/spice-display.c            |    3 +-
 ui/ui-qmp-cmds.c              |  187 ++++++
 ui/vdagent.c                  |    6 +
 ui/vnc-enc-tight.c            |   11 +-
 17 files changed, 776 insertions(+), 692 deletions(-)

-- 
2.41.0



^ permalink raw reply	[flat|nested] 54+ messages in thread

* [PULL 01/52] ui: remove qemu_pixman_color() helper
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
@ 2023-09-04 11:51 ` marcandre.lureau
  2023-09-04 11:51 ` [PULL 02/52] ui: remove qemu_pixman_linebuf_copy() marcandre.lureau
                   ` (51 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:51 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Usage removed in commit e27bd65a72d ("console: switch color_table_rgb to pixman_color_t")

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Message-Id: <20230830093843.3531473-2-marcandre.lureau@redhat.com>
---
 include/ui/qemu-pixman.h |  1 -
 ui/qemu-pixman.c         | 11 -----------
 2 files changed, 12 deletions(-)

diff --git a/include/ui/qemu-pixman.h b/include/ui/qemu-pixman.h
index 0c775604d1..fd78d17124 100644
--- a/include/ui/qemu-pixman.h
+++ b/include/ui/qemu-pixman.h
@@ -78,7 +78,6 @@ pixman_image_t *qemu_pixman_mirror_create(pixman_format_code_t format,
                                           pixman_image_t *image);
 void qemu_pixman_image_unref(pixman_image_t *image);
 
-pixman_color_t qemu_pixman_color(PixelFormat *pf, uint32_t color);
 pixman_image_t *qemu_pixman_glyph_from_vgafont(int height, const uint8_t *font,
                                                unsigned int ch);
 void qemu_pixman_glyph_render(pixman_image_t *glyph,
diff --git a/ui/qemu-pixman.c b/ui/qemu-pixman.c
index e4f024a85e..c5053cd326 100644
--- a/ui/qemu-pixman.c
+++ b/ui/qemu-pixman.c
@@ -226,17 +226,6 @@ void qemu_pixman_image_unref(pixman_image_t *image)
     pixman_image_unref(image);
 }
 
-pixman_color_t qemu_pixman_color(PixelFormat *pf, uint32_t color)
-{
-    pixman_color_t c;
-
-    c.red   = ((color & pf->rmask) >> pf->rshift) << (16 - pf->rbits);
-    c.green = ((color & pf->gmask) >> pf->gshift) << (16 - pf->gbits);
-    c.blue  = ((color & pf->bmask) >> pf->bshift) << (16 - pf->bbits);
-    c.alpha = ((color & pf->amask) >> pf->ashift) << (16 - pf->abits);
-    return c;
-}
-
 pixman_image_t *qemu_pixman_glyph_from_vgafont(int height, const uint8_t *font,
                                                unsigned int ch)
 {
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 02/52] ui: remove qemu_pixman_linebuf_copy()
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
  2023-09-04 11:51 ` [PULL 01/52] ui: remove qemu_pixman_color() helper marcandre.lureau
@ 2023-09-04 11:51 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 03/52] ui/qmp: move screendump to ui-qmp-cmds.c marcandre.lureau
                   ` (50 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:51 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Since commit 43c7d8bd449 ("console: add qemu_pixman_linebuf_copy"), it
seems it was never used.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-3-marcandre.lureau@redhat.com>
---
 include/ui/qemu-pixman.h | 2 --
 ui/qemu-pixman.c         | 8 --------
 2 files changed, 10 deletions(-)

diff --git a/include/ui/qemu-pixman.h b/include/ui/qemu-pixman.h
index fd78d17124..ce4518e4de 100644
--- a/include/ui/qemu-pixman.h
+++ b/include/ui/qemu-pixman.h
@@ -72,8 +72,6 @@ pixman_image_t *qemu_pixman_linebuf_create(pixman_format_code_t format,
                                            int width);
 void qemu_pixman_linebuf_fill(pixman_image_t *linebuf, pixman_image_t *fb,
                               int width, int x, int y);
-void qemu_pixman_linebuf_copy(pixman_image_t *fb, int width, int x, int y,
-                              pixman_image_t *linebuf);
 pixman_image_t *qemu_pixman_mirror_create(pixman_format_code_t format,
                                           pixman_image_t *image);
 void qemu_pixman_image_unref(pixman_image_t *image);
diff --git a/ui/qemu-pixman.c b/ui/qemu-pixman.c
index c5053cd326..be00a96340 100644
--- a/ui/qemu-pixman.c
+++ b/ui/qemu-pixman.c
@@ -200,14 +200,6 @@ void qemu_pixman_linebuf_fill(pixman_image_t *linebuf, pixman_image_t *fb,
                            x, y, 0, 0, 0, 0, width, 1);
 }
 
-/* copy linebuf to framebuffer */
-void qemu_pixman_linebuf_copy(pixman_image_t *fb, int width, int x, int y,
-                              pixman_image_t *linebuf)
-{
-    pixman_image_composite(PIXMAN_OP_SRC, linebuf, NULL, fb,
-                           0, 0, 0, 0, x, y, width, 1);
-}
-
 pixman_image_t *qemu_pixman_mirror_create(pixman_format_code_t format,
                                           pixman_image_t *image)
 {
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 03/52] ui/qmp: move screendump to ui-qmp-cmds.c
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
  2023-09-04 11:51 ` [PULL 01/52] ui: remove qemu_pixman_color() helper marcandre.lureau
  2023-09-04 11:51 ` [PULL 02/52] ui: remove qemu_pixman_linebuf_copy() marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 04/52] ui/vc: replace vc_chr_write() with generic qemu_chr_write() marcandre.lureau
                   ` (49 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

console.c unit is over-crowded. This code is specific to the handling of
the QMP screendump command, so move it in ui-qmp-cmds.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-4-marcandre.lureau@redhat.com>
---
 include/ui/console.h |   1 +
 ui/console.c         | 212 ++++---------------------------------------
 ui/ui-qmp-cmds.c     | 187 ++++++++++++++++++++++++++++++++++++++
 3 files changed, 205 insertions(+), 195 deletions(-)

diff --git a/include/ui/console.h b/include/ui/console.h
index 3e8b22d6c6..1b08b0f8ad 100644
--- a/include/ui/console.h
+++ b/include/ui/console.h
@@ -504,6 +504,7 @@ void qemu_console_set_window_id(QemuConsole *con, int window_id);
 void console_select(unsigned int index);
 void qemu_console_resize(QemuConsole *con, int width, int height);
 DisplaySurface *qemu_console_surface(QemuConsole *con);
+void coroutine_fn qemu_console_co_wait_update(QemuConsole *con);
 
 /* console-gl.c */
 #ifdef CONFIG_OPENGL
diff --git a/ui/console.c b/ui/console.c
index 8da2170a7e..9c17024dbc 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -28,8 +28,8 @@
 #include "qapi/error.h"
 #include "qapi/qapi-commands-ui.h"
 #include "qemu/coroutine.h"
-#include "qemu/error-report.h"
 #include "qemu/fifo8.h"
+#include "qemu/error-report.h"
 #include "qemu/main-loop.h"
 #include "qemu/module.h"
 #include "qemu/option.h"
@@ -37,11 +37,7 @@
 #include "chardev/char.h"
 #include "trace.h"
 #include "exec/memory.h"
-#include "io/channel-file.h"
 #include "qom/object.h"
-#ifdef CONFIG_PNG
-#include <png.h>
-#endif
 
 #define DEFAULT_BACKSCROLL 512
 #define CONSOLE_CURSOR_PERIOD 500
@@ -239,6 +235,22 @@ void graphic_hw_update(QemuConsole *con)
     }
 }
 
+static void graphic_hw_update_bh(void *con)
+{
+    graphic_hw_update(con);
+}
+
+void qemu_console_co_wait_update(QemuConsole *con)
+{
+    if (qemu_co_queue_empty(&con->dump_queue)) {
+        /* Defer the update, it will restart the pending coroutines */
+        aio_bh_schedule_oneshot(qemu_get_aio_context(),
+                                graphic_hw_update_bh, con);
+    }
+    qemu_co_queue_wait(&con->dump_queue, NULL);
+
+}
+
 static void graphic_hw_gl_unblock_timer(void *opaque)
 {
     warn_report("console: no gl-unblock within one second");
@@ -292,196 +304,6 @@ void graphic_hw_invalidate(QemuConsole *con)
     }
 }
 
-#ifdef CONFIG_PNG
-/**
- * png_save: Take a screenshot as PNG
- *
- * Saves screendump as a PNG file
- *
- * Returns true for success or false for error.
- *
- * @fd: File descriptor for PNG file.
- * @image: Image data in pixman format.
- * @errp: Pointer to an error.
- */
-static bool png_save(int fd, pixman_image_t *image, Error **errp)
-{
-    int width = pixman_image_get_width(image);
-    int height = pixman_image_get_height(image);
-    png_struct *png_ptr;
-    png_info *info_ptr;
-    g_autoptr(pixman_image_t) linebuf =
-        qemu_pixman_linebuf_create(PIXMAN_BE_r8g8b8, width);
-    uint8_t *buf = (uint8_t *)pixman_image_get_data(linebuf);
-    FILE *f = fdopen(fd, "wb");
-    int y;
-    if (!f) {
-        error_setg_errno(errp, errno,
-                         "Failed to create file from file descriptor");
-        return false;
-    }
-
-    png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, NULL,
-                                      NULL, NULL);
-    if (!png_ptr) {
-        error_setg(errp, "PNG creation failed. Unable to write struct");
-        fclose(f);
-        return false;
-    }
-
-    info_ptr = png_create_info_struct(png_ptr);
-
-    if (!info_ptr) {
-        error_setg(errp, "PNG creation failed. Unable to write info");
-        fclose(f);
-        png_destroy_write_struct(&png_ptr, &info_ptr);
-        return false;
-    }
-
-    png_init_io(png_ptr, f);
-
-    png_set_IHDR(png_ptr, info_ptr, width, height, 8,
-                 PNG_COLOR_TYPE_RGB, PNG_INTERLACE_NONE,
-                 PNG_COMPRESSION_TYPE_BASE, PNG_FILTER_TYPE_BASE);
-
-    png_write_info(png_ptr, info_ptr);
-
-    for (y = 0; y < height; ++y) {
-        qemu_pixman_linebuf_fill(linebuf, image, width, 0, y);
-        png_write_row(png_ptr, buf);
-    }
-
-    png_write_end(png_ptr, NULL);
-
-    png_destroy_write_struct(&png_ptr, &info_ptr);
-
-    if (fclose(f) != 0) {
-        error_setg_errno(errp, errno,
-                         "PNG creation failed. Unable to close file");
-        return false;
-    }
-
-    return true;
-}
-
-#else /* no png support */
-
-static bool png_save(int fd, pixman_image_t *image, Error **errp)
-{
-    error_setg(errp, "Enable PNG support with libpng for screendump");
-    return false;
-}
-
-#endif /* CONFIG_PNG */
-
-static bool ppm_save(int fd, pixman_image_t *image, Error **errp)
-{
-    int width = pixman_image_get_width(image);
-    int height = pixman_image_get_height(image);
-    g_autoptr(Object) ioc = OBJECT(qio_channel_file_new_fd(fd));
-    g_autofree char *header = NULL;
-    g_autoptr(pixman_image_t) linebuf = NULL;
-    int y;
-
-    trace_ppm_save(fd, image);
-
-    header = g_strdup_printf("P6\n%d %d\n%d\n", width, height, 255);
-    if (qio_channel_write_all(QIO_CHANNEL(ioc),
-                              header, strlen(header), errp) < 0) {
-        return false;
-    }
-
-    linebuf = qemu_pixman_linebuf_create(PIXMAN_BE_r8g8b8, width);
-    for (y = 0; y < height; y++) {
-        qemu_pixman_linebuf_fill(linebuf, image, width, 0, y);
-        if (qio_channel_write_all(QIO_CHANNEL(ioc),
-                                  (char *)pixman_image_get_data(linebuf),
-                                  pixman_image_get_stride(linebuf), errp) < 0) {
-            return false;
-        }
-    }
-
-    return true;
-}
-
-static void graphic_hw_update_bh(void *con)
-{
-    graphic_hw_update(con);
-}
-
-/* Safety: coroutine-only, concurrent-coroutine safe, main thread only */
-void coroutine_fn
-qmp_screendump(const char *filename, const char *device,
-               bool has_head, int64_t head,
-               bool has_format, ImageFormat format, Error **errp)
-{
-    g_autoptr(pixman_image_t) image = NULL;
-    QemuConsole *con;
-    DisplaySurface *surface;
-    int fd;
-
-    if (device) {
-        con = qemu_console_lookup_by_device_name(device, has_head ? head : 0,
-                                                 errp);
-        if (!con) {
-            return;
-        }
-    } else {
-        if (has_head) {
-            error_setg(errp, "'head' must be specified together with 'device'");
-            return;
-        }
-        con = qemu_console_lookup_by_index(0);
-        if (!con) {
-            error_setg(errp, "There is no console to take a screendump from");
-            return;
-        }
-    }
-
-    if (qemu_co_queue_empty(&con->dump_queue)) {
-        /* Defer the update, it will restart the pending coroutines */
-        aio_bh_schedule_oneshot(qemu_get_aio_context(),
-                                graphic_hw_update_bh, con);
-    }
-    qemu_co_queue_wait(&con->dump_queue, NULL);
-
-    /*
-     * All pending coroutines are woken up, while the BQL is held.  No
-     * further graphic update are possible until it is released.  Take
-     * an image ref before that.
-     */
-    surface = qemu_console_surface(con);
-    if (!surface) {
-        error_setg(errp, "no surface");
-        return;
-    }
-    image = pixman_image_ref(surface->image);
-
-    fd = qemu_open_old(filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0666);
-    if (fd == -1) {
-        error_setg(errp, "failed to open file '%s': %s", filename,
-                   strerror(errno));
-        return;
-    }
-
-    /*
-     * The image content could potentially be updated as the coroutine
-     * yields and releases the BQL. It could produce corrupted dump, but
-     * it should be otherwise safe.
-     */
-    if (has_format && format == IMAGE_FORMAT_PNG) {
-        /* PNG format specified for screendump */
-        if (!png_save(fd, image, errp)) {
-            qemu_unlink(filename);
-        }
-    } else {
-        /* PPM format specified/default for screendump */
-        if (!ppm_save(fd, image, errp)) {
-            qemu_unlink(filename);
-        }
-    }
-}
-
 void graphic_hw_text_update(QemuConsole *con, console_ch_t *chardata)
 {
     if (!con) {
diff --git a/ui/ui-qmp-cmds.c b/ui/ui-qmp-cmds.c
index a37a7024f3..debc07d678 100644
--- a/ui/ui-qmp-cmds.c
+++ b/ui/ui-qmp-cmds.c
@@ -14,13 +14,20 @@
  */
 
 #include "qemu/osdep.h"
+
+#include "io/channel-file.h"
 #include "monitor/qmp-helpers.h"
 #include "qapi/qapi-commands-ui.h"
 #include "qapi/qmp/qerror.h"
+#include "qemu/coroutine.h"
 #include "qemu/cutils.h"
+#include "trace.h"
 #include "ui/console.h"
 #include "ui/dbus-display.h"
 #include "ui/qemu-spice.h"
+#ifdef CONFIG_PNG
+#include <png.h>
+#endif
 
 void qmp_set_password(SetPasswordOptions *opts, Error **errp)
 {
@@ -204,3 +211,183 @@ void qmp_client_migrate_info(const char *protocol, const char *hostname,
 
     error_setg(errp, QERR_INVALID_PARAMETER_VALUE, "protocol", "'spice'");
 }
+
+#ifdef CONFIG_PNG
+/**
+ * png_save: Take a screenshot as PNG
+ *
+ * Saves screendump as a PNG file
+ *
+ * Returns true for success or false for error.
+ *
+ * @fd: File descriptor for PNG file.
+ * @image: Image data in pixman format.
+ * @errp: Pointer to an error.
+ */
+static bool png_save(int fd, pixman_image_t *image, Error **errp)
+{
+    int width = pixman_image_get_width(image);
+    int height = pixman_image_get_height(image);
+    png_struct *png_ptr;
+    png_info *info_ptr;
+    g_autoptr(pixman_image_t) linebuf =
+        qemu_pixman_linebuf_create(PIXMAN_BE_r8g8b8, width);
+    uint8_t *buf = (uint8_t *)pixman_image_get_data(linebuf);
+    FILE *f = fdopen(fd, "wb");
+    int y;
+    if (!f) {
+        error_setg_errno(errp, errno,
+                         "Failed to create file from file descriptor");
+        return false;
+    }
+
+    png_ptr = png_create_write_struct(PNG_LIBPNG_VER_STRING, NULL,
+                                      NULL, NULL);
+    if (!png_ptr) {
+        error_setg(errp, "PNG creation failed. Unable to write struct");
+        fclose(f);
+        return false;
+    }
+
+    info_ptr = png_create_info_struct(png_ptr);
+
+    if (!info_ptr) {
+        error_setg(errp, "PNG creation failed. Unable to write info");
+        fclose(f);
+        png_destroy_write_struct(&png_ptr, &info_ptr);
+        return false;
+    }
+
+    png_init_io(png_ptr, f);
+
+    png_set_IHDR(png_ptr, info_ptr, width, height, 8,
+                 PNG_COLOR_TYPE_RGB, PNG_INTERLACE_NONE,
+                 PNG_COMPRESSION_TYPE_BASE, PNG_FILTER_TYPE_BASE);
+
+    png_write_info(png_ptr, info_ptr);
+
+    for (y = 0; y < height; ++y) {
+        qemu_pixman_linebuf_fill(linebuf, image, width, 0, y);
+        png_write_row(png_ptr, buf);
+    }
+
+    png_write_end(png_ptr, NULL);
+
+    png_destroy_write_struct(&png_ptr, &info_ptr);
+
+    if (fclose(f) != 0) {
+        error_setg_errno(errp, errno,
+                         "PNG creation failed. Unable to close file");
+        return false;
+    }
+
+    return true;
+}
+
+#else /* no png support */
+
+static bool png_save(int fd, pixman_image_t *image, Error **errp)
+{
+    error_setg(errp, "Enable PNG support with libpng for screendump");
+    return false;
+}
+
+#endif /* CONFIG_PNG */
+
+static bool ppm_save(int fd, pixman_image_t *image, Error **errp)
+{
+    int width = pixman_image_get_width(image);
+    int height = pixman_image_get_height(image);
+    g_autoptr(Object) ioc = OBJECT(qio_channel_file_new_fd(fd));
+    g_autofree char *header = NULL;
+    g_autoptr(pixman_image_t) linebuf = NULL;
+    int y;
+
+    trace_ppm_save(fd, image);
+
+    header = g_strdup_printf("P6\n%d %d\n%d\n", width, height, 255);
+    if (qio_channel_write_all(QIO_CHANNEL(ioc),
+                              header, strlen(header), errp) < 0) {
+        return false;
+    }
+
+    linebuf = qemu_pixman_linebuf_create(PIXMAN_BE_r8g8b8, width);
+    for (y = 0; y < height; y++) {
+        qemu_pixman_linebuf_fill(linebuf, image, width, 0, y);
+        if (qio_channel_write_all(QIO_CHANNEL(ioc),
+                                  (char *)pixman_image_get_data(linebuf),
+                                  pixman_image_get_stride(linebuf), errp) < 0) {
+            return false;
+        }
+    }
+
+    return true;
+}
+
+/* Safety: coroutine-only, concurrent-coroutine safe, main thread only */
+void coroutine_fn
+qmp_screendump(const char *filename, const char *device,
+               bool has_head, int64_t head,
+               bool has_format, ImageFormat format, Error **errp)
+{
+    g_autoptr(pixman_image_t) image = NULL;
+    QemuConsole *con;
+    DisplaySurface *surface;
+    int fd;
+
+    if (device) {
+        con = qemu_console_lookup_by_device_name(device, has_head ? head : 0,
+                                                 errp);
+        if (!con) {
+            return;
+        }
+    } else {
+        if (has_head) {
+            error_setg(errp, "'head' must be specified together with 'device'");
+            return;
+        }
+        con = qemu_console_lookup_by_index(0);
+        if (!con) {
+            error_setg(errp, "There is no console to take a screendump from");
+            return;
+        }
+    }
+
+    qemu_console_co_wait_update(con);
+
+    /*
+     * All pending coroutines are woken up, while the BQL is held.  No
+     * further graphic update are possible until it is released.  Take
+     * an image ref before that.
+     */
+    surface = qemu_console_surface(con);
+    if (!surface) {
+        error_setg(errp, "no surface");
+        return;
+    }
+    image = pixman_image_ref(surface->image);
+
+    fd = qemu_open_old(filename, O_WRONLY | O_CREAT | O_TRUNC | O_BINARY, 0666);
+    if (fd == -1) {
+        error_setg(errp, "failed to open file '%s': %s", filename,
+                   strerror(errno));
+        return;
+    }
+
+    /*
+     * The image content could potentially be updated as the coroutine
+     * yields and releases the BQL. It could produce corrupted dump, but
+     * it should be otherwise safe.
+     */
+    if (has_format && format == IMAGE_FORMAT_PNG) {
+        /* PNG format specified for screendump */
+        if (!png_save(fd, image, errp)) {
+            qemu_unlink(filename);
+        }
+    } else {
+        /* PPM format specified/default for screendump */
+        if (!ppm_save(fd, image, errp)) {
+            qemu_unlink(filename);
+        }
+    }
+}
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 04/52] ui/vc: replace vc_chr_write() with generic qemu_chr_write()
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (2 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 03/52] ui/qmp: move screendump to ui-qmp-cmds.c marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 05/52] ui/vc: drop have_text marcandre.lureau
                   ` (48 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

We shouldn't call the callback directly, but use the chardev API, unless
there is a clear reason.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Message-Id: <20230830093843.3531473-5-marcandre.lureau@redhat.com>
---
 ui/console.c | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 9c17024dbc..a448e4d283 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1169,13 +1169,13 @@ void kbd_put_keysym_console(QemuConsole *s, int keysym)
             *q++ = '[';
             *q++ = keysym & 0xff;
         } else if (s->echo && (keysym == '\r' || keysym == '\n')) {
-            vc_chr_write(s->chr, (const uint8_t *) "\r", 1);
+            qemu_chr_write(s->chr, (uint8_t *)"\r", 1, true);
             *q++ = '\n';
         } else {
             *q++ = keysym;
         }
         if (s->echo) {
-            vc_chr_write(s->chr, buf, q - buf);
+            qemu_chr_write(s->chr, buf, q - buf, true);
         }
         num_free = fifo8_num_free(&s->out_fifo);
         fifo8_push_all(&s->out_fifo, buf, MIN(num_free, q - buf));
@@ -2474,7 +2474,7 @@ static void text_console_do_init(Chardev *chr, DisplayState *ds)
 
         s->t_attrib.bgcol = QEMU_COLOR_BLUE;
         msg = g_strdup_printf("%s console\r\n", chr->label);
-        vc_chr_write(chr, (uint8_t *)msg, strlen(msg));
+        qemu_chr_write(chr, (uint8_t *)msg, strlen(msg), true);
         g_free(msg);
         s->t_attrib = s->t_attrib_default;
     }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 05/52] ui/vc: drop have_text
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (3 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 04/52] ui/vc: replace vc_chr_write() with generic qemu_chr_write() marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 06/52] ui/console: console_select() regardless of have_gfx marcandre.lureau
                   ` (47 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

If there are no "text" listener, the callback will simply be ignored.
The rest of text handling can be done cheaply.

This allows to remove some dependency on DisplayState from VC
implementation.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-6-marcandre.lureau@redhat.com>
---
 ui/console.c | 42 +++++++++++++-----------------------------
 1 file changed, 13 insertions(+), 29 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index a448e4d283..bec2d1a40a 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -133,7 +133,6 @@ struct DisplayState {
     uint64_t update_interval;
     bool refreshing;
     bool have_gfx;
-    bool have_text;
 
     QLIST_HEAD(, DisplayChangeListener) listeners;
 };
@@ -185,7 +184,6 @@ static void gui_setup_refresh(DisplayState *ds)
     DisplayChangeListener *dcl;
     bool need_timer = false;
     bool have_gfx = false;
-    bool have_text = false;
 
     QLIST_FOREACH(dcl, &ds->listeners, next) {
         if (dcl->ops->dpy_refresh != NULL) {
@@ -194,9 +192,6 @@ static void gui_setup_refresh(DisplayState *ds)
         if (dcl->ops->dpy_gfx_update != NULL) {
             have_gfx = true;
         }
-        if (dcl->ops->dpy_text_update != NULL) {
-            have_text = true;
-        }
     }
 
     if (need_timer && ds->gui_timer == NULL) {
@@ -209,7 +204,6 @@ static void gui_setup_refresh(DisplayState *ds)
     }
 
     ds->have_gfx = have_gfx;
-    ds->have_text = have_text;
 }
 
 void graphic_hw_update_done(QemuConsole *con)
@@ -456,9 +450,7 @@ static void update_xy(QemuConsole *s, int x, int y)
     TextCell *c;
     int y1, y2;
 
-    if (s->ds->have_text) {
-        text_update_xy(s, x, y);
-    }
+    text_update_xy(s, x, y);
 
     y1 = (s->y_base + y) % s->total_height;
     y2 = y1 - s->y_displayed;
@@ -482,9 +474,7 @@ static void console_show_cursor(QemuConsole *s, int show)
     int y, y1;
     int x = s->x;
 
-    if (s->ds->have_text) {
-        s->cursor_invalidate = 1;
-    }
+    s->cursor_invalidate = 1;
 
     if (x >= s->width) {
         x = s->width - 1;
@@ -513,13 +503,11 @@ static void console_refresh(QemuConsole *s)
     TextCell *c;
     int x, y, y1;
 
-    if (s->ds->have_text) {
-        s->text_x[0] = 0;
-        s->text_y[0] = 0;
-        s->text_x[1] = s->width - 1;
-        s->text_y[1] = s->height - 1;
-        s->cursor_invalidate = 1;
-    }
+    s->text_x[0] = 0;
+    s->text_y[0] = 0;
+    s->text_x[1] = s->width - 1;
+    s->text_y[1] = s->height - 1;
+    s->cursor_invalidate = 1;
 
     vga_fill_rect(s, 0, 0, surface_width(surface), surface_height(surface),
                   color_table_rgb[0][QEMU_COLOR_BLACK]);
@@ -594,12 +582,10 @@ static void console_put_lf(QemuConsole *s)
             c++;
         }
         if (s->y_displayed == s->y_base) {
-            if (s->ds->have_text) {
-                s->text_x[0] = 0;
-                s->text_y[0] = 0;
-                s->text_x[1] = s->width - 1;
-                s->text_y[1] = s->height - 1;
-            }
+            s->text_x[0] = 0;
+            s->text_y[0] = 0;
+            s->text_x[1] = s->width - 1;
+            s->text_y[1] = s->height - 1;
 
             vga_bitblt(s, 0, FONT_HEIGHT, 0, 0,
                        s->width * FONT_WIDTH,
@@ -1069,9 +1055,7 @@ void console_select(unsigned int index)
                 displaychangelistener_display_console(dcl, s, NULL);
             }
         }
-        if (ds->have_text) {
-            dpy_text_resize(s, s->width, s->height);
-        }
+        dpy_text_resize(s, s->width, s->height);
         text_console_update_cursor(NULL);
     }
 }
@@ -1239,7 +1223,7 @@ static void text_console_invalidate(void *opaque)
 {
     QemuConsole *s = (QemuConsole *) opaque;
 
-    if (s->ds->have_text && s->console_type == TEXT_CONSOLE) {
+    if (s->console_type == TEXT_CONSOLE) {
         text_console_resize(s);
     }
     console_refresh(s);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 06/52] ui/console: console_select() regardless of have_gfx
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (4 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 05/52] ui/vc: drop have_text marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 07/52] ui/console: call dpy_gfx_update() " marcandre.lureau
                   ` (46 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Even if we don't have a gfx listener, we should call
displaychangelistener_display_console() which handle that case correctly.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-7-marcandre.lureau@redhat.com>
---
 ui/console.c | 10 ++++------
 1 file changed, 4 insertions(+), 6 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index bec2d1a40a..14717a6f4d 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1047,13 +1047,11 @@ void console_select(unsigned int index)
         DisplayState *ds = s->ds;
 
         active_console = s;
-        if (ds->have_gfx) {
-            QLIST_FOREACH(dcl, &ds->listeners, next) {
-                if (dcl->con != NULL) {
-                    continue;
-                }
-                displaychangelistener_display_console(dcl, s, NULL);
+        QLIST_FOREACH (dcl, &ds->listeners, next) {
+            if (dcl->con != NULL) {
+                continue;
             }
+            displaychangelistener_display_console(dcl, s, NULL);
         }
         dpy_text_resize(s, s->width, s->height);
         text_console_update_cursor(NULL);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 07/52] ui/console: call dpy_gfx_update() regardless of have_gfx
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (5 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 06/52] ui/console: console_select() regardless of have_gfx marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 08/52] ui/console: drop have_gfx marcandre.lureau
                   ` (45 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

The function will handle the case when no listeners are gfx, without
extra meaningful cost.

This allows to get rid of DisplayState dependency in VC implementation.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-8-marcandre.lureau@redhat.com>
---
 ui/console.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ui/console.c b/ui/console.c
index 14717a6f4d..2bc4c153de 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1087,7 +1087,7 @@ static int vc_chr_write(Chardev *chr, const uint8_t *buf, int len)
         console_putchar(s, buf[i]);
     }
     console_show_cursor(s, 1);
-    if (s->ds->have_gfx && s->update_x0 < s->update_x1) {
+    if (s->update_x0 < s->update_x1) {
         dpy_gfx_update(s, s->update_x0, s->update_y0,
                        s->update_x1 - s->update_x0,
                        s->update_y1 - s->update_y0);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 08/52] ui/console: drop have_gfx
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (6 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 07/52] ui/console: call dpy_gfx_update() " marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 09/52] ui/console: get the DisplayState from new_console() marcandre.lureau
                   ` (44 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

All usages have been removed.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-9-marcandre.lureau@redhat.com>
---
 ui/console.c | 7 -------
 1 file changed, 7 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 2bc4c153de..fc1836782d 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -132,7 +132,6 @@ struct DisplayState {
     uint64_t last_update;
     uint64_t update_interval;
     bool refreshing;
-    bool have_gfx;
 
     QLIST_HEAD(, DisplayChangeListener) listeners;
 };
@@ -183,15 +182,11 @@ static void gui_setup_refresh(DisplayState *ds)
 {
     DisplayChangeListener *dcl;
     bool need_timer = false;
-    bool have_gfx = false;
 
     QLIST_FOREACH(dcl, &ds->listeners, next) {
         if (dcl->ops->dpy_refresh != NULL) {
             need_timer = true;
         }
-        if (dcl->ops->dpy_gfx_update != NULL) {
-            have_gfx = true;
-        }
     }
 
     if (need_timer && ds->gui_timer == NULL) {
@@ -202,8 +197,6 @@ static void gui_setup_refresh(DisplayState *ds)
         timer_free(ds->gui_timer);
         ds->gui_timer = NULL;
     }
-
-    ds->have_gfx = have_gfx;
 }
 
 void graphic_hw_update_done(QemuConsole *con)
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 09/52] ui/console: get the DisplayState from new_console()
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (7 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 08/52] ui/console: drop have_gfx marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 10/52] ui/console: new_console() cannot fail marcandre.lureau
                   ` (43 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

There is no obvious reason to defer text console initialization. We can
simply take the global display state in new_console().

This simplify somewhat the code to allow moving the VC to a separate unit.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-10-marcandre.lureau@redhat.com>
---
 ui/console.c | 27 ++++++++-------------------
 1 file changed, 8 insertions(+), 19 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index fc1836782d..24cfd31ad6 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -143,7 +143,7 @@ static QTAILQ_HEAD(, QemuConsole) consoles =
 static bool cursor_visible_phase;
 static QEMUTimer *cursor_timer;
 
-static void text_console_do_init(Chardev *chr, DisplayState *ds);
+static void text_console_do_init(Chardev *chr);
 static void dpy_refresh(DisplayState *s);
 static DisplayState *get_alloc_displaystate(void);
 static void text_console_update_cursor_timer(void);
@@ -1249,9 +1249,9 @@ static void text_console_update(void *opaque, console_ch_t *chardata)
     }
 }
 
-static QemuConsole *new_console(DisplayState *ds, console_type_t console_type,
-                                uint32_t head)
+static QemuConsole *new_console(console_type_t console_type, uint32_t head)
 {
+    DisplayState *ds = get_alloc_displaystate();
     Object *obj;
     QemuConsole *s;
     int i;
@@ -2049,13 +2049,7 @@ DisplayState *init_displaystate(void)
     gchar *name;
     QemuConsole *con;
 
-    get_alloc_displaystate();
     QTAILQ_FOREACH(con, &consoles, next) {
-        if (con->console_type != GRAPHIC_CONSOLE &&
-            con->ds == NULL) {
-            text_console_do_init(con->chr, display_state);
-        }
-
         /* Hook up into the qom tree here (not in new_console()), once
          * all QemuConsoles are created and the order / numbering
          * doesn't change any more */
@@ -2085,10 +2079,8 @@ QemuConsole *graphic_console_init(DeviceState *dev, uint32_t head,
     int width = 640;
     int height = 480;
     QemuConsole *s;
-    DisplayState *ds;
     DisplaySurface *surface;
 
-    ds = get_alloc_displaystate();
     s = qemu_console_lookup_unused();
     if (s) {
         trace_console_gfx_reuse(s->index);
@@ -2096,7 +2088,7 @@ QemuConsole *graphic_console_init(DeviceState *dev, uint32_t head,
         height = qemu_console_get_height(s, 0);
     } else {
         trace_console_gfx_new();
-        s = new_console(ds, GRAPHIC_CONSOLE, head);
+        s = new_console(GRAPHIC_CONSOLE, head);
         s->ui_timer = timer_new_ms(QEMU_CLOCK_REALTIME,
                                    dpy_set_ui_info_timer, s);
     }
@@ -2405,7 +2397,7 @@ static const GraphicHwOps text_console_ops = {
     .text_update = text_console_update,
 };
 
-static void text_console_do_init(Chardev *chr, DisplayState *ds)
+static void text_console_do_init(Chardev *chr)
 {
     VCChardev *drv = VC_CHARDEV(chr);
     QemuConsole *s = drv->console;
@@ -2413,7 +2405,6 @@ static void text_console_do_init(Chardev *chr, DisplayState *ds)
     int g_height = 24 * FONT_HEIGHT;
 
     fifo8_create(&s->out_fifo, 16);
-    s->ds = ds;
 
     s->y_displayed = 0;
     s->y_base = 0;
@@ -2482,9 +2473,9 @@ static void vc_chr_open(Chardev *chr,
 
     trace_console_txt_new(width, height);
     if (width == 0 || height == 0) {
-        s = new_console(NULL, TEXT_CONSOLE, 0);
+        s = new_console(TEXT_CONSOLE, 0);
     } else {
-        s = new_console(NULL, TEXT_CONSOLE_FIXED_SIZE, 0);
+        s = new_console(TEXT_CONSOLE_FIXED_SIZE, 0);
         s->scanout.kind = SCANOUT_SURFACE;
         s->surface = qemu_create_displaysurface(width, height);
     }
@@ -2497,9 +2488,7 @@ static void vc_chr_open(Chardev *chr,
     s->chr = chr;
     drv->console = s;
 
-    if (display_state) {
-        text_console_do_init(chr, display_state);
-    }
+    text_console_do_init(chr);
 
     /* console/chardev init sometimes completes elsewhere in a 2nd
      * stage, so defer OPENED events until they are fully initialized
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 10/52] ui/console: new_console() cannot fail
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (8 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 09/52] ui/console: get the DisplayState from new_console() marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 11/52] ui/vc: VC always has a DisplayState now marcandre.lureau
                   ` (42 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

There is no code path that could allow a NULL return there.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-11-marcandre.lureau@redhat.com>
---
 ui/console.c | 5 -----
 1 file changed, 5 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 24cfd31ad6..ddec68feb7 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -2480,11 +2480,6 @@ static void vc_chr_open(Chardev *chr,
         s->surface = qemu_create_displaysurface(width, height);
     }
 
-    if (!s) {
-        error_setg(errp, "cannot create text console");
-        return;
-    }
-
     s->chr = chr;
     drv->console = s;
 
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 11/52] ui/vc: VC always has a DisplayState now
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (9 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 10/52] ui/console: new_console() cannot fail marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 12/52] ui/vc: move VCChardev declaration at the top marcandre.lureau
                   ` (41 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-12-marcandre.lureau@redhat.com>
---
 ui/console.c | 4 ----
 1 file changed, 4 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index ddec68feb7..f97db295f6 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1067,10 +1067,6 @@ static int vc_chr_write(Chardev *chr, const uint8_t *buf, int len)
     QemuConsole *s = drv->console;
     int i;
 
-    if (!s->ds) {
-        return 0;
-    }
-
     s->update_x0 = s->width * FONT_WIDTH;
     s->update_y0 = s->height * FONT_HEIGHT;
     s->update_x1 = 0;
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 12/52] ui/vc: move VCChardev declaration at the top
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (10 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 11/52] ui/vc: VC always has a DisplayState now marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 13/52] ui/vc: replace variable with static text attributes default marcandre.lureau
                   ` (40 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

To allow easier refactoring in following patches.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-13-marcandre.lureau@redhat.com>
---
 ui/console.c | 12 ++++++------
 1 file changed, 6 insertions(+), 6 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index f97db295f6..5c8e3ad1df 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -127,6 +127,12 @@ struct QemuConsole {
     QTAILQ_ENTRY(QemuConsole) next;
 };
 
+struct VCChardev {
+    Chardev parent;
+    QemuConsole *console;
+};
+typedef struct VCChardev VCChardev;
+
 struct DisplayState {
     QEMUTimer *gui_timer;
     uint64_t last_update;
@@ -1051,12 +1057,6 @@ void console_select(unsigned int index)
     }
 }
 
-struct VCChardev {
-    Chardev parent;
-    QemuConsole *console;
-};
-typedef struct VCChardev VCChardev;
-
 #define TYPE_CHARDEV_VC "chardev-vc"
 DECLARE_INSTANCE_CHECKER(VCChardev, VC_CHARDEV,
                          TYPE_CHARDEV_VC)
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 13/52] ui/vc: replace variable with static text attributes default
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (11 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 12/52] ui/vc: move VCChardev declaration at the top marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 14/52] ui/vc: fold text_update_xy() marcandre.lureau
                   ` (39 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-14-marcandre.lureau@redhat.com>
---
 ui/console.c | 30 +++++++++++++-----------------
 1 file changed, 13 insertions(+), 17 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 5c8e3ad1df..d1855f3fcf 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -52,6 +52,11 @@ typedef struct TextAttributes {
     uint8_t unvisible:1;
 } TextAttributes;
 
+#define TEXT_ATTRIBUTES_DEFAULT ((TextAttributes) { \
+    .fgcol = QEMU_COLOR_WHITE,                      \
+    .bgcol = QEMU_COLOR_BLACK                       \
+})
+
 typedef struct TextCell {
     uint8_t ch;
     TextAttributes t_attrib;
@@ -104,7 +109,6 @@ struct QemuConsole {
     int x_saved, y_saved;
     int y_displayed;
     int y_base;
-    TextAttributes t_attrib_default; /* default text attributes */
     TextAttributes t_attrib; /* currently active text attributes */
     TextCell *cells;
     int text_x[2], text_y[2], cursor_invalidate;
@@ -413,7 +417,7 @@ static void text_console_resize(QemuConsole *s)
         }
         for(x = w1; x < s->width; x++) {
             c->ch = ' ';
-            c->t_attrib = s->t_attrib_default;
+            c->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
             c++;
         }
     }
@@ -486,7 +490,7 @@ static void console_show_cursor(QemuConsole *s, int show)
     if (y < s->height) {
         c = &s->cells[y1 * s->width + x];
         if (show && cursor_visible_phase) {
-            TextAttributes t_attrib = s->t_attrib_default;
+            TextAttributes t_attrib = TEXT_ATTRIBUTES_DEFAULT;
             t_attrib.invers = !(t_attrib.invers); /* invert fg and bg */
             vga_putcharxy(s, x, y, c->ch, &t_attrib);
         } else {
@@ -577,7 +581,7 @@ static void console_put_lf(QemuConsole *s)
         c = &s->cells[y1 * s->width];
         for(x = 0; x < s->width; x++) {
             c->ch = ' ';
-            c->t_attrib = s->t_attrib_default;
+            c->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
             c++;
         }
         if (s->y_displayed == s->y_base) {
@@ -591,7 +595,7 @@ static void console_put_lf(QemuConsole *s)
                        (s->height - 1) * FONT_HEIGHT);
             vga_fill_rect(s, 0, (s->height - 1) * FONT_HEIGHT,
                           s->width * FONT_WIDTH, FONT_HEIGHT,
-                          color_table_rgb[0][s->t_attrib_default.bgcol]);
+                          color_table_rgb[0][TEXT_ATTRIBUTES_DEFAULT.bgcol]);
             s->update_x0 = 0;
             s->update_y0 = 0;
             s->update_x1 = s->width * FONT_WIDTH;
@@ -611,7 +615,7 @@ static void console_handle_escape(QemuConsole *s)
     for (i=0; i<s->nb_esc_params; i++) {
         switch (s->esc_params[i]) {
             case 0: /* reset all console attributes to default */
-                s->t_attrib = s->t_attrib_default;
+                s->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
                 break;
             case 1:
                 s->t_attrib.bold = 1;
@@ -705,7 +709,7 @@ static void console_clear_xy(QemuConsole *s, int x, int y)
     }
     TextCell *c = &s->cells[y1 * s->width + x];
     c->ch = ' ';
-    c->t_attrib = s->t_attrib_default;
+    c->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
     update_xy(s, x, y);
 }
 
@@ -2419,16 +2423,8 @@ static void text_console_do_init(Chardev *chr)
     s->hw_ops = &text_console_ops;
     s->hw = s;
 
-    /* Set text attribute defaults */
-    s->t_attrib_default.bold = 0;
-    s->t_attrib_default.uline = 0;
-    s->t_attrib_default.blink = 0;
-    s->t_attrib_default.invers = 0;
-    s->t_attrib_default.unvisible = 0;
-    s->t_attrib_default.fgcol = QEMU_COLOR_WHITE;
-    s->t_attrib_default.bgcol = QEMU_COLOR_BLACK;
     /* set current text attributes to default */
-    s->t_attrib = s->t_attrib_default;
+    s->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
     text_console_resize(s);
 
     if (chr->label) {
@@ -2438,7 +2434,7 @@ static void text_console_do_init(Chardev *chr)
         msg = g_strdup_printf("%s console\r\n", chr->label);
         qemu_chr_write(chr, (uint8_t *)msg, strlen(msg), true);
         g_free(msg);
-        s->t_attrib = s->t_attrib_default;
+        s->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
     }
 
     qemu_chr_be_event(chr, CHR_EVENT_OPENED);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 14/52] ui/vc: fold text_update_xy()
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (12 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 13/52] ui/vc: replace variable with static text attributes default marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 15/52] ui/vc: pass VCCharDev to VC-specific functions marcandre.lureau
                   ` (38 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-15-marcandre.lureau@redhat.com>
---
 ui/console.c | 13 ++++---------
 1 file changed, 4 insertions(+), 9 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index d1855f3fcf..405aedfcbd 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -425,14 +425,6 @@ static void text_console_resize(QemuConsole *s)
     s->cells = cells;
 }
 
-static inline void text_update_xy(QemuConsole *s, int x, int y)
-{
-    s->text_x[0] = MIN(s->text_x[0], x);
-    s->text_x[1] = MAX(s->text_x[1], x);
-    s->text_y[0] = MIN(s->text_y[0], y);
-    s->text_y[1] = MAX(s->text_y[1], y);
-}
-
 static void invalidate_xy(QemuConsole *s, int x, int y)
 {
     if (!qemu_console_is_visible(s)) {
@@ -453,7 +445,10 @@ static void update_xy(QemuConsole *s, int x, int y)
     TextCell *c;
     int y1, y2;
 
-    text_update_xy(s, x, y);
+    s->text_x[0] = MIN(s->text_x[0], x);
+    s->text_x[1] = MAX(s->text_x[1], x);
+    s->text_y[0] = MIN(s->text_y[0], y);
+    s->text_y[1] = MAX(s->text_y[1], y);
 
     y1 = (s->y_base + y) % s->total_height;
     y2 = y1 - s->y_displayed;
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 15/52] ui/vc: pass VCCharDev to VC-specific functions
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (13 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 14/52] ui/vc: fold text_update_xy() marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 16/52] ui/vc: move VCCharDev specific fields out of QemuConsole marcandre.lureau
                   ` (37 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Even though they actually use more of QemuConsole at this point, it
makes it clearer those functions are only used from the chardev
implementation.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-16-marcandre.lureau@redhat.com>
---
 ui/console.c | 70 +++++++++++++++++++++++++++++-----------------------
 1 file changed, 39 insertions(+), 31 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 405aedfcbd..f9ed012e1c 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -440,8 +440,9 @@ static void invalidate_xy(QemuConsole *s, int x, int y)
         s->update_y1 = (y + 1) * FONT_HEIGHT;
 }
 
-static void update_xy(QemuConsole *s, int x, int y)
+static void vc_update_xy(VCChardev *vc, int x, int y)
 {
+    QemuConsole *s = vc->console;
     TextCell *c;
     int y1, y2;
 
@@ -555,8 +556,9 @@ static void console_scroll(QemuConsole *s, int ydelta)
     console_refresh(s);
 }
 
-static void console_put_lf(QemuConsole *s)
+static void vc_put_lf(VCChardev *vc)
 {
+    QemuConsole *s = vc->console;
     TextCell *c;
     int x, y1;
 
@@ -603,8 +605,9 @@ static void console_put_lf(QemuConsole *s)
  * NOTE: I know this code is not very efficient (checking every color for it
  * self) but it is more readable and better maintainable.
  */
-static void console_handle_escape(QemuConsole *s)
+static void vc_handle_escape(VCChardev *vc)
 {
+    QemuConsole *s = vc->console;
     int i;
 
     for (i=0; i<s->nb_esc_params; i++) {
@@ -696,8 +699,9 @@ static void console_handle_escape(QemuConsole *s)
     }
 }
 
-static void console_clear_xy(QemuConsole *s, int x, int y)
+static void vc_clear_xy(VCChardev *vc, int x, int y)
 {
+    QemuConsole *s = vc->console;
     int y1 = (s->y_base + y) % s->total_height;
     if (x >= s->width) {
         x = s->width - 1;
@@ -705,37 +709,40 @@ static void console_clear_xy(QemuConsole *s, int x, int y)
     TextCell *c = &s->cells[y1 * s->width + x];
     c->ch = ' ';
     c->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
-    update_xy(s, x, y);
+    vc_update_xy(vc, x, y);
 }
 
-static void console_put_one(QemuConsole *s, int ch)
+static void vc_put_one(VCChardev *vc, int ch)
 {
+    QemuConsole *s = vc->console;
     TextCell *c;
     int y1;
     if (s->x >= s->width) {
         /* line wrap */
         s->x = 0;
-        console_put_lf(s);
+        vc_put_lf(vc);
     }
     y1 = (s->y_base + s->y) % s->total_height;
     c = &s->cells[y1 * s->width + s->x];
     c->ch = ch;
     c->t_attrib = s->t_attrib;
-    update_xy(s, s->x, s->y);
+    vc_update_xy(vc, s->x, s->y);
     s->x++;
 }
 
-static void console_respond_str(QemuConsole *s, const char *buf)
+static void vc_respond_str(VCChardev *vc, const char *buf)
 {
     while (*buf) {
-        console_put_one(s, *buf);
+        vc_put_one(vc, *buf);
         buf++;
     }
 }
 
 /* set cursor, checking bounds */
-static void set_cursor(QemuConsole *s, int x, int y)
+static void vc_set_cursor(VCChardev *vc, int x, int y)
 {
+    QemuConsole *s = vc->console;
+
     if (x < 0) {
         x = 0;
     }
@@ -753,8 +760,9 @@ static void set_cursor(QemuConsole *s, int x, int y)
     s->y = y;
 }
 
-static void console_putchar(QemuConsole *s, int ch)
+static void vc_putchar(VCChardev *vc, int ch)
 {
+    QemuConsole *s = vc->console;
     int i;
     int x, y;
     char response[40];
@@ -766,7 +774,7 @@ static void console_putchar(QemuConsole *s, int ch)
             s->x = 0;
             break;
         case '\n':  /* newline */
-            console_put_lf(s);
+            vc_put_lf(vc);
             break;
         case '\b':  /* backspace */
             if (s->x > 0)
@@ -775,7 +783,7 @@ static void console_putchar(QemuConsole *s, int ch)
         case '\t':  /* tabspace */
             if (s->x + (8 - (s->x % 8)) > s->width) {
                 s->x = 0;
-                console_put_lf(s);
+                vc_put_lf(vc);
             } else {
                 s->x = s->x + (8 - (s->x % 8));
             }
@@ -793,7 +801,7 @@ static void console_putchar(QemuConsole *s, int ch)
             s->state = TTY_STATE_ESC;
             break;
         default:
-            console_put_one(s, ch);
+            vc_put_one(vc, ch);
             break;
         }
         break;
@@ -831,37 +839,37 @@ static void console_putchar(QemuConsole *s, int ch)
                 if (s->esc_params[0] == 0) {
                     s->esc_params[0] = 1;
                 }
-                set_cursor(s, s->x, s->y - s->esc_params[0]);
+                vc_set_cursor(vc, s->x, s->y - s->esc_params[0]);
                 break;
             case 'B':
                 /* move cursor down */
                 if (s->esc_params[0] == 0) {
                     s->esc_params[0] = 1;
                 }
-                set_cursor(s, s->x, s->y + s->esc_params[0]);
+                vc_set_cursor(vc, s->x, s->y + s->esc_params[0]);
                 break;
             case 'C':
                 /* move cursor right */
                 if (s->esc_params[0] == 0) {
                     s->esc_params[0] = 1;
                 }
-                set_cursor(s, s->x + s->esc_params[0], s->y);
+                vc_set_cursor(vc, s->x + s->esc_params[0], s->y);
                 break;
             case 'D':
                 /* move cursor left */
                 if (s->esc_params[0] == 0) {
                     s->esc_params[0] = 1;
                 }
-                set_cursor(s, s->x - s->esc_params[0], s->y);
+                vc_set_cursor(vc, s->x - s->esc_params[0], s->y);
                 break;
             case 'G':
                 /* move cursor to column */
-                set_cursor(s, s->esc_params[0] - 1, s->y);
+                vc_set_cursor(vc, s->esc_params[0] - 1, s->y);
                 break;
             case 'f':
             case 'H':
                 /* move cursor to row, column */
-                set_cursor(s, s->esc_params[1] - 1, s->esc_params[0] - 1);
+                vc_set_cursor(vc, s->esc_params[1] - 1, s->esc_params[0] - 1);
                 break;
             case 'J':
                 switch (s->esc_params[0]) {
@@ -872,7 +880,7 @@ static void console_putchar(QemuConsole *s, int ch)
                             if (y == s->y && x < s->x) {
                                 continue;
                             }
-                            console_clear_xy(s, x, y);
+                            vc_clear_xy(vc, x, y);
                         }
                     }
                     break;
@@ -883,7 +891,7 @@ static void console_putchar(QemuConsole *s, int ch)
                             if (y == s->y && x > s->x) {
                                 break;
                             }
-                            console_clear_xy(s, x, y);
+                            vc_clear_xy(vc, x, y);
                         }
                     }
                     break;
@@ -891,7 +899,7 @@ static void console_putchar(QemuConsole *s, int ch)
                     /* clear entire screen */
                     for (y = 0; y <= s->height; y++) {
                         for (x = 0; x < s->width; x++) {
-                            console_clear_xy(s, x, y);
+                            vc_clear_xy(vc, x, y);
                         }
                     }
                     break;
@@ -902,38 +910,38 @@ static void console_putchar(QemuConsole *s, int ch)
                 case 0:
                     /* clear to eol */
                     for(x = s->x; x < s->width; x++) {
-                        console_clear_xy(s, x, s->y);
+                        vc_clear_xy(vc, x, s->y);
                     }
                     break;
                 case 1:
                     /* clear from beginning of line */
                     for (x = 0; x <= s->x && x < s->width; x++) {
-                        console_clear_xy(s, x, s->y);
+                        vc_clear_xy(vc, x, s->y);
                     }
                     break;
                 case 2:
                     /* clear entire line */
                     for(x = 0; x < s->width; x++) {
-                        console_clear_xy(s, x, s->y);
+                        vc_clear_xy(vc, x, s->y);
                     }
                     break;
                 }
                 break;
             case 'm':
-                console_handle_escape(s);
+                vc_handle_escape(vc);
                 break;
             case 'n':
                 switch (s->esc_params[0]) {
                 case 5:
                     /* report console status (always succeed)*/
-                    console_respond_str(s, "\033[0n");
+                    vc_respond_str(vc, "\033[0n");
                     break;
                 case 6:
                     /* report cursor position */
                     sprintf(response, "\033[%d;%dR",
                            (s->y_base + s->y) % s->total_height + 1,
                             s->x + 1);
-                    console_respond_str(s, response);
+                    vc_respond_str(vc, response);
                     break;
                 }
                 break;
@@ -1072,7 +1080,7 @@ static int vc_chr_write(Chardev *chr, const uint8_t *buf, int len)
     s->update_y1 = 0;
     console_show_cursor(s, 0);
     for(i = 0; i < len; i++) {
-        console_putchar(s, buf[i]);
+        vc_putchar(drv, buf[i]);
     }
     console_show_cursor(s, 1);
     if (s->update_x0 < s->update_x1) {
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 16/52] ui/vc: move VCCharDev specific fields out of QemuConsole
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (14 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 15/52] ui/vc: pass VCCharDev to VC-specific functions marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 17/52] ui/console: use OBJECT_DEFINE_TYPE for QemuConsole marcandre.lureau
                   ` (36 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-17-marcandre.lureau@redhat.com>
---
 ui/console.c | 147 +++++++++++++++++++++++++--------------------------
 1 file changed, 73 insertions(+), 74 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index f9ed012e1c..1336a1be6c 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -106,10 +106,8 @@ struct QemuConsole {
     int total_height;
     int backscroll_height;
     int x, y;
-    int x_saved, y_saved;
     int y_displayed;
     int y_base;
-    TextAttributes t_attrib; /* currently active text attributes */
     TextCell *cells;
     int text_x[2], text_y[2], cursor_invalidate;
     int echo;
@@ -119,10 +117,6 @@ struct QemuConsole {
     int update_x1;
     int update_y1;
 
-    enum TTYState state;
-    int esc_params[MAX_ESC_PARAMS];
-    int nb_esc_params;
-
     Chardev *chr;
     /* fifo for key pressed */
     Fifo8 out_fifo;
@@ -134,6 +128,12 @@ struct QemuConsole {
 struct VCChardev {
     Chardev parent;
     QemuConsole *console;
+
+    enum TTYState state;
+    int esc_params[MAX_ESC_PARAMS];
+    int nb_esc_params;
+    TextAttributes t_attrib; /* currently active text attributes */
+    int x_saved, y_saved;
 };
 typedef struct VCChardev VCChardev;
 
@@ -607,93 +607,92 @@ static void vc_put_lf(VCChardev *vc)
  */
 static void vc_handle_escape(VCChardev *vc)
 {
-    QemuConsole *s = vc->console;
     int i;
 
-    for (i=0; i<s->nb_esc_params; i++) {
-        switch (s->esc_params[i]) {
+    for (i = 0; i < vc->nb_esc_params; i++) {
+        switch (vc->esc_params[i]) {
             case 0: /* reset all console attributes to default */
-                s->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
+                vc->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
                 break;
             case 1:
-                s->t_attrib.bold = 1;
+                vc->t_attrib.bold = 1;
                 break;
             case 4:
-                s->t_attrib.uline = 1;
+                vc->t_attrib.uline = 1;
                 break;
             case 5:
-                s->t_attrib.blink = 1;
+                vc->t_attrib.blink = 1;
                 break;
             case 7:
-                s->t_attrib.invers = 1;
+                vc->t_attrib.invers = 1;
                 break;
             case 8:
-                s->t_attrib.unvisible = 1;
+                vc->t_attrib.unvisible = 1;
                 break;
             case 22:
-                s->t_attrib.bold = 0;
+                vc->t_attrib.bold = 0;
                 break;
             case 24:
-                s->t_attrib.uline = 0;
+                vc->t_attrib.uline = 0;
                 break;
             case 25:
-                s->t_attrib.blink = 0;
+                vc->t_attrib.blink = 0;
                 break;
             case 27:
-                s->t_attrib.invers = 0;
+                vc->t_attrib.invers = 0;
                 break;
             case 28:
-                s->t_attrib.unvisible = 0;
+                vc->t_attrib.unvisible = 0;
                 break;
             /* set foreground color */
             case 30:
-                s->t_attrib.fgcol = QEMU_COLOR_BLACK;
+                vc->t_attrib.fgcol = QEMU_COLOR_BLACK;
                 break;
             case 31:
-                s->t_attrib.fgcol = QEMU_COLOR_RED;
+                vc->t_attrib.fgcol = QEMU_COLOR_RED;
                 break;
             case 32:
-                s->t_attrib.fgcol = QEMU_COLOR_GREEN;
+                vc->t_attrib.fgcol = QEMU_COLOR_GREEN;
                 break;
             case 33:
-                s->t_attrib.fgcol = QEMU_COLOR_YELLOW;
+                vc->t_attrib.fgcol = QEMU_COLOR_YELLOW;
                 break;
             case 34:
-                s->t_attrib.fgcol = QEMU_COLOR_BLUE;
+                vc->t_attrib.fgcol = QEMU_COLOR_BLUE;
                 break;
             case 35:
-                s->t_attrib.fgcol = QEMU_COLOR_MAGENTA;
+                vc->t_attrib.fgcol = QEMU_COLOR_MAGENTA;
                 break;
             case 36:
-                s->t_attrib.fgcol = QEMU_COLOR_CYAN;
+                vc->t_attrib.fgcol = QEMU_COLOR_CYAN;
                 break;
             case 37:
-                s->t_attrib.fgcol = QEMU_COLOR_WHITE;
+                vc->t_attrib.fgcol = QEMU_COLOR_WHITE;
                 break;
             /* set background color */
             case 40:
-                s->t_attrib.bgcol = QEMU_COLOR_BLACK;
+                vc->t_attrib.bgcol = QEMU_COLOR_BLACK;
                 break;
             case 41:
-                s->t_attrib.bgcol = QEMU_COLOR_RED;
+                vc->t_attrib.bgcol = QEMU_COLOR_RED;
                 break;
             case 42:
-                s->t_attrib.bgcol = QEMU_COLOR_GREEN;
+                vc->t_attrib.bgcol = QEMU_COLOR_GREEN;
                 break;
             case 43:
-                s->t_attrib.bgcol = QEMU_COLOR_YELLOW;
+                vc->t_attrib.bgcol = QEMU_COLOR_YELLOW;
                 break;
             case 44:
-                s->t_attrib.bgcol = QEMU_COLOR_BLUE;
+                vc->t_attrib.bgcol = QEMU_COLOR_BLUE;
                 break;
             case 45:
-                s->t_attrib.bgcol = QEMU_COLOR_MAGENTA;
+                vc->t_attrib.bgcol = QEMU_COLOR_MAGENTA;
                 break;
             case 46:
-                s->t_attrib.bgcol = QEMU_COLOR_CYAN;
+                vc->t_attrib.bgcol = QEMU_COLOR_CYAN;
                 break;
             case 47:
-                s->t_attrib.bgcol = QEMU_COLOR_WHITE;
+                vc->t_attrib.bgcol = QEMU_COLOR_WHITE;
                 break;
         }
     }
@@ -725,7 +724,7 @@ static void vc_put_one(VCChardev *vc, int ch)
     y1 = (s->y_base + s->y) % s->total_height;
     c = &s->cells[y1 * s->width + s->x];
     c->ch = ch;
-    c->t_attrib = s->t_attrib;
+    c->t_attrib = vc->t_attrib;
     vc_update_xy(vc, s->x, s->y);
     s->x++;
 }
@@ -767,7 +766,7 @@ static void vc_putchar(VCChardev *vc, int ch)
     int x, y;
     char response[40];
 
-    switch(s->state) {
+    switch(vc->state) {
     case TTY_STATE_NORM:
         switch(ch) {
         case '\r':  /* carriage return */
@@ -798,7 +797,7 @@ static void vc_putchar(VCChardev *vc, int ch)
             /* SO (shift out), character set 1 (ignored) */
             break;
         case 27:    /* esc (introducing an escape sequence) */
-            s->state = TTY_STATE_ESC;
+            vc->state = TTY_STATE_ESC;
             break;
         default:
             vc_put_one(vc, ch);
@@ -808,71 +807,71 @@ static void vc_putchar(VCChardev *vc, int ch)
     case TTY_STATE_ESC: /* check if it is a terminal escape sequence */
         if (ch == '[') {
             for(i=0;i<MAX_ESC_PARAMS;i++)
-                s->esc_params[i] = 0;
-            s->nb_esc_params = 0;
-            s->state = TTY_STATE_CSI;
+                vc->esc_params[i] = 0;
+            vc->nb_esc_params = 0;
+            vc->state = TTY_STATE_CSI;
         } else {
-            s->state = TTY_STATE_NORM;
+            vc->state = TTY_STATE_NORM;
         }
         break;
     case TTY_STATE_CSI: /* handle escape sequence parameters */
         if (ch >= '0' && ch <= '9') {
-            if (s->nb_esc_params < MAX_ESC_PARAMS) {
-                int *param = &s->esc_params[s->nb_esc_params];
+            if (vc->nb_esc_params < MAX_ESC_PARAMS) {
+                int *param = &vc->esc_params[vc->nb_esc_params];
                 int digit = (ch - '0');
 
                 *param = (*param <= (INT_MAX - digit) / 10) ?
                          *param * 10 + digit : INT_MAX;
             }
         } else {
-            if (s->nb_esc_params < MAX_ESC_PARAMS)
-                s->nb_esc_params++;
+            if (vc->nb_esc_params < MAX_ESC_PARAMS)
+                vc->nb_esc_params++;
             if (ch == ';' || ch == '?') {
                 break;
             }
-            trace_console_putchar_csi(s->esc_params[0], s->esc_params[1],
-                                      ch, s->nb_esc_params);
-            s->state = TTY_STATE_NORM;
+            trace_console_putchar_csi(vc->esc_params[0], vc->esc_params[1],
+                                      ch, vc->nb_esc_params);
+            vc->state = TTY_STATE_NORM;
             switch(ch) {
             case 'A':
                 /* move cursor up */
-                if (s->esc_params[0] == 0) {
-                    s->esc_params[0] = 1;
+                if (vc->esc_params[0] == 0) {
+                    vc->esc_params[0] = 1;
                 }
-                vc_set_cursor(vc, s->x, s->y - s->esc_params[0]);
+                vc_set_cursor(vc, s->x, s->y - vc->esc_params[0]);
                 break;
             case 'B':
                 /* move cursor down */
-                if (s->esc_params[0] == 0) {
-                    s->esc_params[0] = 1;
+                if (vc->esc_params[0] == 0) {
+                    vc->esc_params[0] = 1;
                 }
-                vc_set_cursor(vc, s->x, s->y + s->esc_params[0]);
+                vc_set_cursor(vc, s->x, s->y + vc->esc_params[0]);
                 break;
             case 'C':
                 /* move cursor right */
-                if (s->esc_params[0] == 0) {
-                    s->esc_params[0] = 1;
+                if (vc->esc_params[0] == 0) {
+                    vc->esc_params[0] = 1;
                 }
-                vc_set_cursor(vc, s->x + s->esc_params[0], s->y);
+                vc_set_cursor(vc, s->x + vc->esc_params[0], s->y);
                 break;
             case 'D':
                 /* move cursor left */
-                if (s->esc_params[0] == 0) {
-                    s->esc_params[0] = 1;
+                if (vc->esc_params[0] == 0) {
+                    vc->esc_params[0] = 1;
                 }
-                vc_set_cursor(vc, s->x - s->esc_params[0], s->y);
+                vc_set_cursor(vc, s->x - vc->esc_params[0], s->y);
                 break;
             case 'G':
                 /* move cursor to column */
-                vc_set_cursor(vc, s->esc_params[0] - 1, s->y);
+                vc_set_cursor(vc, vc->esc_params[0] - 1, s->y);
                 break;
             case 'f':
             case 'H':
                 /* move cursor to row, column */
-                vc_set_cursor(vc, s->esc_params[1] - 1, s->esc_params[0] - 1);
+                vc_set_cursor(vc, vc->esc_params[1] - 1, vc->esc_params[0] - 1);
                 break;
             case 'J':
-                switch (s->esc_params[0]) {
+                switch (vc->esc_params[0]) {
                 case 0:
                     /* clear to end of screen */
                     for (y = s->y; y < s->height; y++) {
@@ -906,7 +905,7 @@ static void vc_putchar(VCChardev *vc, int ch)
                 }
                 break;
             case 'K':
-                switch (s->esc_params[0]) {
+                switch (vc->esc_params[0]) {
                 case 0:
                     /* clear to eol */
                     for(x = s->x; x < s->width; x++) {
@@ -931,7 +930,7 @@ static void vc_putchar(VCChardev *vc, int ch)
                 vc_handle_escape(vc);
                 break;
             case 'n':
-                switch (s->esc_params[0]) {
+                switch (vc->esc_params[0]) {
                 case 5:
                     /* report console status (always succeed)*/
                     vc_respond_str(vc, "\033[0n");
@@ -947,13 +946,13 @@ static void vc_putchar(VCChardev *vc, int ch)
                 break;
             case 's':
                 /* save cursor position */
-                s->x_saved = s->x;
-                s->y_saved = s->y;
+                vc->x_saved = s->x;
+                vc->y_saved = s->y;
                 break;
             case 'u':
                 /* restore cursor position */
-                s->x = s->x_saved;
-                s->y = s->y_saved;
+                s->x = vc->x_saved;
+                s->y = vc->y_saved;
                 break;
             default:
                 trace_console_putchar_unhandled(ch);
@@ -2427,17 +2426,17 @@ static void text_console_do_init(Chardev *chr)
     s->hw = s;
 
     /* set current text attributes to default */
-    s->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
+    drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
     text_console_resize(s);
 
     if (chr->label) {
         char *msg;
 
-        s->t_attrib.bgcol = QEMU_COLOR_BLUE;
+        drv->t_attrib.bgcol = QEMU_COLOR_BLUE;
         msg = g_strdup_printf("%s console\r\n", chr->label);
         qemu_chr_write(chr, (uint8_t *)msg, strlen(msg), true);
         g_free(msg);
-        s->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
+        drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
     }
 
     qemu_chr_be_event(chr, CHR_EVENT_OPENED);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 17/52] ui/console: use OBJECT_DEFINE_TYPE for QemuConsole
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (15 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 16/52] ui/vc: move VCCharDev specific fields out of QemuConsole marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 18/52] ui/console: change new_console() to use object initialization marcandre.lureau
                   ` (35 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

The following patch will move some object initialization to the
corresponding handlers.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-18-marcandre.lureau@redhat.com>
---
 ui/console.c | 31 +++++++++++++++++--------------
 1 file changed, 17 insertions(+), 14 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 1336a1be6c..14fb38c661 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -125,6 +125,8 @@ struct QemuConsole {
     QTAILQ_ENTRY(QemuConsole) next;
 };
 
+OBJECT_DEFINE_TYPE(QemuConsole, qemu_console, QEMU_CONSOLE, OBJECT)
+
 struct VCChardev {
     Chardev parent;
     QemuConsole *console;
@@ -1313,6 +1315,21 @@ static QemuConsole *new_console(console_type_t console_type, uint32_t head)
     return s;
 }
 
+static void
+qemu_console_finalize(Object *obj)
+{
+}
+
+static void
+qemu_console_class_init(ObjectClass *oc, void *data)
+{
+}
+
+static void
+qemu_console_init(Object *obj)
+{
+}
+
 #ifdef WIN32
 void qemu_displaysurface_win32_set_handle(DisplaySurface *surface,
                                           HANDLE h, uint32_t offset)
@@ -2646,13 +2663,6 @@ void qemu_chr_parse_vc(QemuOpts *opts, ChardevBackend *backend, Error **errp)
     }
 }
 
-static const TypeInfo qemu_console_info = {
-    .name = TYPE_QEMU_CONSOLE,
-    .parent = TYPE_OBJECT,
-    .instance_size = sizeof(QemuConsole),
-    .class_size = sizeof(QemuConsoleClass),
-};
-
 static void char_vc_class_init(ObjectClass *oc, void *data)
 {
     ChardevClass *cc = CHARDEV_CLASS(oc);
@@ -2678,10 +2688,3 @@ void qemu_console_early_init(void)
         type_register(&char_vc_type_info);
     }
 }
-
-static void register_types(void)
-{
-    type_register_static(&qemu_console_info);
-}
-
-type_init(register_types);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 18/52] ui/console: change new_console() to use object initialization
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (16 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 17/52] ui/console: use OBJECT_DEFINE_TYPE for QemuConsole marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 19/52] ui/console: introduce different console objects marcandre.lureau
                   ` (34 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Object construction should be done in respective object instance and
class handlers.

Introduce qemu_console_register() to split out the registration logic.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-19-marcandre.lureau@redhat.com>
---
 ui/console.c | 92 ++++++++++++++++++++++++++++++++--------------------
 1 file changed, 56 insertions(+), 36 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 14fb38c661..bdecfe7306 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -27,6 +27,7 @@
 #include "hw/qdev-core.h"
 #include "qapi/error.h"
 #include "qapi/qapi-commands-ui.h"
+#include "qapi/visitor.h"
 #include "qemu/coroutine.h"
 #include "qemu/fifo8.h"
 #include "qemu/error-report.h"
@@ -1253,39 +1254,24 @@ static void text_console_update(void *opaque, console_ch_t *chardata)
     }
 }
 
-static QemuConsole *new_console(console_type_t console_type, uint32_t head)
+static void
+qemu_console_register(QemuConsole *c, console_type_t console_type)
 {
-    DisplayState *ds = get_alloc_displaystate();
-    Object *obj;
-    QemuConsole *s;
     int i;
 
-    obj = object_new(TYPE_QEMU_CONSOLE);
-    s = QEMU_CONSOLE(obj);
-    qemu_co_queue_init(&s->dump_queue);
-    s->head = head;
-    object_property_add_link(obj, "device", TYPE_DEVICE,
-                             (Object **)&s->device,
-                             object_property_allow_set_link,
-                             OBJ_PROP_LINK_STRONG);
-    object_property_add_uint32_ptr(obj, "head", &s->head,
-                                   OBJ_PROP_FLAG_READ);
-
     if (!active_console || ((active_console->console_type != GRAPHIC_CONSOLE) &&
-        (console_type == GRAPHIC_CONSOLE))) {
-        active_console = s;
+                            (console_type == GRAPHIC_CONSOLE))) {
+        active_console = c;
     }
-    s->ds = ds;
-    s->console_type = console_type;
-    s->window_id = -1;
+    c->console_type = console_type;
 
     if (QTAILQ_EMPTY(&consoles)) {
-        s->index = 0;
-        QTAILQ_INSERT_TAIL(&consoles, s, next);
+        c->index = 0;
+        QTAILQ_INSERT_TAIL(&consoles, c, next);
     } else if (console_type != GRAPHIC_CONSOLE || phase_check(PHASE_MACHINE_READY)) {
         QemuConsole *last = QTAILQ_LAST(&consoles);
-        s->index = last->index + 1;
-        QTAILQ_INSERT_TAIL(&consoles, s, next);
+        c->index = last->index + 1;
+        QTAILQ_INSERT_TAIL(&consoles, c, next);
     } else {
         /*
          * HACK: Put graphical consoles before text consoles.
@@ -1293,41 +1279,75 @@ static QemuConsole *new_console(console_type_t console_type, uint32_t head)
          * Only do that for coldplugged devices.  After initial device
          * initialization we will not renumber the consoles any more.
          */
-        QemuConsole *c = QTAILQ_FIRST(&consoles);
+        QemuConsole *it = QTAILQ_FIRST(&consoles);
 
-        while (QTAILQ_NEXT(c, next) != NULL &&
-               c->console_type == GRAPHIC_CONSOLE) {
-            c = QTAILQ_NEXT(c, next);
+        while (QTAILQ_NEXT(it, next) != NULL &&
+               it->console_type == GRAPHIC_CONSOLE) {
+            it = QTAILQ_NEXT(it, next);
         }
-        if (c->console_type == GRAPHIC_CONSOLE) {
+        if (it->console_type == GRAPHIC_CONSOLE) {
             /* have no text consoles */
-            s->index = c->index + 1;
-            QTAILQ_INSERT_AFTER(&consoles, c, s, next);
+            c->index = it->index + 1;
+            QTAILQ_INSERT_AFTER(&consoles, it, c, next);
         } else {
-            s->index = c->index;
-            QTAILQ_INSERT_BEFORE(c, s, next);
+            c->index = it->index;
+            QTAILQ_INSERT_BEFORE(it, c, next);
             /* renumber text consoles */
-            for (i = s->index + 1; c != NULL; c = QTAILQ_NEXT(c, next), i++) {
-                c->index = i;
+            for (i = c->index + 1; it != NULL; it = QTAILQ_NEXT(it, next), i++) {
+                it->index = i;
             }
         }
     }
-    return s;
 }
 
 static void
 qemu_console_finalize(Object *obj)
 {
+    /* TODO: should unregister from consoles and free itself  */
+}
+
+static void
+qemu_console_prop_get_head(Object *obj, Visitor *v, const char *name,
+                           void *opaque, Error **errp)
+{
+    QemuConsole *c = QEMU_CONSOLE(obj);
+
+    visit_type_uint32(v, name, &c->head, errp);
 }
 
 static void
 qemu_console_class_init(ObjectClass *oc, void *data)
 {
+    object_class_property_add_link(oc, "device", TYPE_DEVICE,
+                                   offsetof(QemuConsole, device),
+                                   object_property_allow_set_link,
+                                   OBJ_PROP_LINK_STRONG);
+    object_class_property_add(oc, "head", "uint32",
+                              qemu_console_prop_get_head,
+                              NULL, NULL, NULL);
 }
 
 static void
 qemu_console_init(Object *obj)
 {
+    QemuConsole *c = QEMU_CONSOLE(obj);
+    DisplayState *ds = get_alloc_displaystate();
+
+    qemu_co_queue_init(&c->dump_queue);
+    c->ds = ds;
+    c->window_id = -1;
+}
+
+static QemuConsole *new_console(console_type_t console_type,
+                                uint32_t head)
+{
+    QemuConsole *c = QEMU_CONSOLE(object_new(TYPE_QEMU_CONSOLE));
+
+    c->head = head;
+    /* TODO: move to console_init() once there is a type hierarchy */
+    qemu_console_register(c, console_type);
+
+    return c;
 }
 
 #ifdef WIN32
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 19/52] ui/console: introduce different console objects
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (17 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 18/52] ui/console: change new_console() to use object initialization marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 20/52] ui/console: instantiate a specific console type marcandre.lureau
                   ` (33 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Boilerplate code to introduce different object types for the different
console types.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-20-marcandre.lureau@redhat.com>
---
 ui/console.c | 84 ++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 file changed, 84 insertions(+)

diff --git a/ui/console.c b/ui/console.c
index bdecfe7306..4ca5064cc9 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -128,6 +128,45 @@ struct QemuConsole {
 
 OBJECT_DEFINE_TYPE(QemuConsole, qemu_console, QEMU_CONSOLE, OBJECT)
 
+typedef struct QemuGraphicConsole {
+    QemuConsole parent;
+} QemuGraphicConsole;
+
+typedef QemuConsoleClass QemuGraphicConsoleClass;
+
+#define TYPE_QEMU_GRAPHIC_CONSOLE "qemu-graphic-console"
+OBJECT_DECLARE_SIMPLE_TYPE(QemuGraphicConsole, QEMU_GRAPHIC_CONSOLE)
+OBJECT_DEFINE_TYPE(QemuGraphicConsole, qemu_graphic_console, QEMU_GRAPHIC_CONSOLE, QEMU_CONSOLE)
+
+#define QEMU_IS_GRAPHIC_CONSOLE(c) \
+    object_dynamic_cast(OBJECT(c), TYPE_QEMU_GRAPHIC_CONSOLE)
+
+typedef struct QemuTextConsole {
+    QemuConsole parent;
+} QemuTextConsole;
+
+typedef QemuConsoleClass QemuTextConsoleClass;
+
+#define TYPE_QEMU_TEXT_CONSOLE "qemu-text-console"
+OBJECT_DECLARE_SIMPLE_TYPE(QemuTextConsole, QEMU_TEXT_CONSOLE)
+OBJECT_DEFINE_TYPE(QemuTextConsole, qemu_text_console, QEMU_TEXT_CONSOLE, QEMU_CONSOLE)
+
+#define QEMU_IS_TEXT_CONSOLE(c) \
+    object_dynamic_cast(OBJECT(c), TYPE_QEMU_TEXT_CONSOLE)
+
+typedef struct QemuFixedTextConsole {
+    QemuTextConsole parent;
+} QemuFixedTextConsole;
+
+typedef QemuTextConsoleClass QemuFixedTextConsoleClass;
+
+#define TYPE_QEMU_FIXED_TEXT_CONSOLE "qemu-fixed-text-console"
+OBJECT_DECLARE_SIMPLE_TYPE(QemuFixedTextConsole, QEMU_FIXED_TEXT_CONSOLE)
+OBJECT_DEFINE_TYPE(QemuFixedTextConsole, qemu_fixed_text_console, QEMU_FIXED_TEXT_CONSOLE, QEMU_TEXT_CONSOLE)
+
+#define QEMU_IS_FIXED_TEXT_CONSOLE(c) \
+    object_dynamic_cast(OBJECT(c), TYPE_QEMU_FIXED_TEXT_CONSOLE)
+
 struct VCChardev {
     Chardev parent;
     QemuConsole *console;
@@ -1338,6 +1377,51 @@ qemu_console_init(Object *obj)
     c->window_id = -1;
 }
 
+static void
+qemu_graphic_console_finalize(Object *obj)
+{
+}
+
+static void
+qemu_graphic_console_class_init(ObjectClass *oc, void *data)
+{
+}
+
+static void
+qemu_graphic_console_init(Object *obj)
+{
+}
+
+static void
+qemu_text_console_finalize(Object *obj)
+{
+}
+
+static void
+qemu_text_console_class_init(ObjectClass *oc, void *data)
+{
+}
+
+static void
+qemu_text_console_init(Object *obj)
+{
+}
+
+static void
+qemu_fixed_text_console_finalize(Object *obj)
+{
+}
+
+static void
+qemu_fixed_text_console_class_init(ObjectClass *oc, void *data)
+{
+}
+
+static void
+qemu_fixed_text_console_init(Object *obj)
+{
+}
+
 static QemuConsole *new_console(console_type_t console_type,
                                 uint32_t head)
 {
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 20/52] ui/console: instantiate a specific console type
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (18 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 19/52] ui/console: introduce different console objects marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 21/52] ui/console: register the console from qemu_console_init() marcandre.lureau
                   ` (32 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

This will allow to move code/data to the specific console types.

Replace console_type_t with object type check.

QemuConsole can be abstract.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-21-marcandre.lureau@redhat.com>
---
 ui/console.c | 47 +++++++++++++++++++----------------------------
 1 file changed, 19 insertions(+), 28 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 4ca5064cc9..dd8e8db525 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -71,17 +71,10 @@ enum TTYState {
     TTY_STATE_CSI,
 };
 
-typedef enum {
-    GRAPHIC_CONSOLE,
-    TEXT_CONSOLE,
-    TEXT_CONSOLE_FIXED_SIZE
-} console_type_t;
-
 struct QemuConsole {
     Object parent;
 
     int index;
-    console_type_t console_type;
     DisplayState *ds;
     DisplaySurface *surface;
     DisplayScanout scanout;
@@ -126,7 +119,7 @@ struct QemuConsole {
     QTAILQ_ENTRY(QemuConsole) next;
 };
 
-OBJECT_DEFINE_TYPE(QemuConsole, qemu_console, QEMU_CONSOLE, OBJECT)
+OBJECT_DEFINE_ABSTRACT_TYPE(QemuConsole, qemu_console, QEMU_CONSOLE, OBJECT)
 
 typedef struct QemuGraphicConsole {
     QemuConsole parent;
@@ -1156,7 +1149,7 @@ void kbd_put_keysym_console(QemuConsole *s, int keysym)
     int c;
     uint32_t num_free;
 
-    if (!s || (s->console_type == GRAPHIC_CONSOLE))
+    if (!s || QEMU_IS_GRAPHIC_CONSOLE(s))
         return;
 
     switch(keysym) {
@@ -1258,7 +1251,7 @@ static void text_console_invalidate(void *opaque)
 {
     QemuConsole *s = (QemuConsole *) opaque;
 
-    if (s->console_type == TEXT_CONSOLE) {
+    if (QEMU_IS_TEXT_CONSOLE(s) && !QEMU_IS_FIXED_TEXT_CONSOLE(s)) {
         text_console_resize(s);
     }
     console_refresh(s);
@@ -1294,20 +1287,19 @@ static void text_console_update(void *opaque, console_ch_t *chardata)
 }
 
 static void
-qemu_console_register(QemuConsole *c, console_type_t console_type)
+qemu_console_register(QemuConsole *c)
 {
     int i;
 
-    if (!active_console || ((active_console->console_type != GRAPHIC_CONSOLE) &&
-                            (console_type == GRAPHIC_CONSOLE))) {
+    if (!active_console || (!QEMU_IS_GRAPHIC_CONSOLE(active_console) &&
+                            QEMU_IS_GRAPHIC_CONSOLE(c))) {
         active_console = c;
     }
-    c->console_type = console_type;
 
     if (QTAILQ_EMPTY(&consoles)) {
         c->index = 0;
         QTAILQ_INSERT_TAIL(&consoles, c, next);
-    } else if (console_type != GRAPHIC_CONSOLE || phase_check(PHASE_MACHINE_READY)) {
+    } else if (!QEMU_IS_GRAPHIC_CONSOLE(c) || phase_check(PHASE_MACHINE_READY)) {
         QemuConsole *last = QTAILQ_LAST(&consoles);
         c->index = last->index + 1;
         QTAILQ_INSERT_TAIL(&consoles, c, next);
@@ -1320,11 +1312,10 @@ qemu_console_register(QemuConsole *c, console_type_t console_type)
          */
         QemuConsole *it = QTAILQ_FIRST(&consoles);
 
-        while (QTAILQ_NEXT(it, next) != NULL &&
-               it->console_type == GRAPHIC_CONSOLE) {
+        while (QTAILQ_NEXT(it, next) != NULL && QEMU_IS_GRAPHIC_CONSOLE(it)) {
             it = QTAILQ_NEXT(it, next);
         }
-        if (it->console_type == GRAPHIC_CONSOLE) {
+        if (QEMU_IS_GRAPHIC_CONSOLE(it)) {
             /* have no text consoles */
             c->index = it->index + 1;
             QTAILQ_INSERT_AFTER(&consoles, it, c, next);
@@ -1422,14 +1413,14 @@ qemu_fixed_text_console_init(Object *obj)
 {
 }
 
-static QemuConsole *new_console(console_type_t console_type,
+static QemuConsole *new_console(const char *typename,
                                 uint32_t head)
 {
-    QemuConsole *c = QEMU_CONSOLE(object_new(TYPE_QEMU_CONSOLE));
+    QemuConsole *c = QEMU_CONSOLE(object_new(typename));
 
     c->head = head;
     /* TODO: move to console_init() once there is a type hierarchy */
-    qemu_console_register(c, console_type);
+    qemu_console_register(c);
 
     return c;
 }
@@ -2211,7 +2202,7 @@ QemuConsole *graphic_console_init(DeviceState *dev, uint32_t head,
         height = qemu_console_get_height(s, 0);
     } else {
         trace_console_gfx_new();
-        s = new_console(GRAPHIC_CONSOLE, head);
+        s = new_console(TYPE_QEMU_GRAPHIC_CONSOLE, head);
         s->ui_timer = timer_new_ms(QEMU_CLOCK_REALTIME,
                                    dpy_set_ui_info_timer, s);
     }
@@ -2345,7 +2336,7 @@ bool qemu_console_is_graphic(QemuConsole *con)
     if (con == NULL) {
         con = active_console;
     }
-    return con && (con->console_type == GRAPHIC_CONSOLE);
+    return con && QEMU_IS_GRAPHIC_CONSOLE(con);
 }
 
 bool qemu_console_is_fixedsize(QemuConsole *con)
@@ -2353,7 +2344,7 @@ bool qemu_console_is_fixedsize(QemuConsole *con)
     if (con == NULL) {
         con = active_console;
     }
-    return con && (con->console_type != TEXT_CONSOLE);
+    return con && (QEMU_IS_GRAPHIC_CONSOLE(con) || QEMU_IS_FIXED_TEXT_CONSOLE(con));
 }
 
 bool qemu_console_is_gl_blocked(QemuConsole *con)
@@ -2389,7 +2380,7 @@ bool qemu_console_is_multihead(DeviceState *dev)
 
 char *qemu_console_get_label(QemuConsole *con)
 {
-    if (con->console_type == GRAPHIC_CONSOLE) {
+    if (QEMU_IS_GRAPHIC_CONSOLE(con)) {
         if (con->device) {
             DeviceState *dev;
             bool multihead;
@@ -2588,9 +2579,9 @@ static void vc_chr_open(Chardev *chr,
 
     trace_console_txt_new(width, height);
     if (width == 0 || height == 0) {
-        s = new_console(TEXT_CONSOLE, 0);
+        s = new_console(TYPE_QEMU_TEXT_CONSOLE, 0);
     } else {
-        s = new_console(TEXT_CONSOLE_FIXED_SIZE, 0);
+        s = new_console(TYPE_QEMU_FIXED_TEXT_CONSOLE, 0);
         s->scanout.kind = SCANOUT_SURFACE;
         s->surface = qemu_create_displaysurface(width, height);
     }
@@ -2610,7 +2601,7 @@ void qemu_console_resize(QemuConsole *s, int width, int height)
 {
     DisplaySurface *surface = qemu_console_surface(s);
 
-    assert(s->console_type == GRAPHIC_CONSOLE);
+    assert(QEMU_IS_GRAPHIC_CONSOLE(s));
 
     if ((s->scanout.kind != SCANOUT_SURFACE ||
          (surface && surface->flags & QEMU_ALLOCATED_FLAG)) &&
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 21/52] ui/console: register the console from qemu_console_init()
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (19 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 20/52] ui/console: instantiate a specific console type marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 22/52] ui/console: remove new_console() marcandre.lureau
                   ` (31 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-22-marcandre.lureau@redhat.com>
---
 ui/console.c | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index dd8e8db525..02a24eaf5d 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1366,6 +1366,7 @@ qemu_console_init(Object *obj)
     qemu_co_queue_init(&c->dump_queue);
     c->ds = ds;
     c->window_id = -1;
+    qemu_console_register(c);
 }
 
 static void
@@ -1419,8 +1420,6 @@ static QemuConsole *new_console(const char *typename,
     QemuConsole *c = QEMU_CONSOLE(object_new(typename));
 
     c->head = head;
-    /* TODO: move to console_init() once there is a type hierarchy */
-    qemu_console_register(c);
 
     return c;
 }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 22/52] ui/console: remove new_console()
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (20 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 21/52] ui/console: register the console from qemu_console_init() marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 23/52] ui/console: specialize console_lookup_unused() marcandre.lureau
                   ` (30 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

The constructor helper isn't of much used now.

"head" is only specified for graphic console (and default to 0), and we
are going to move it to QemuGraphicConsole next.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-23-marcandre.lureau@redhat.com>
---
 ui/console.c | 19 +++++--------------
 1 file changed, 5 insertions(+), 14 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 02a24eaf5d..e0e4f980d7 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1414,16 +1414,6 @@ qemu_fixed_text_console_init(Object *obj)
 {
 }
 
-static QemuConsole *new_console(const char *typename,
-                                uint32_t head)
-{
-    QemuConsole *c = QEMU_CONSOLE(object_new(typename));
-
-    c->head = head;
-
-    return c;
-}
-
 #ifdef WIN32
 void qemu_displaysurface_win32_set_handle(DisplaySurface *surface,
                                           HANDLE h, uint32_t offset)
@@ -2163,7 +2153,7 @@ DisplayState *init_displaystate(void)
     QemuConsole *con;
 
     QTAILQ_FOREACH(con, &consoles, next) {
-        /* Hook up into the qom tree here (not in new_console()), once
+        /* Hook up into the qom tree here (not in object_new()), once
          * all QemuConsoles are created and the order / numbering
          * doesn't change any more */
         name = g_strdup_printf("console[%d]", con->index);
@@ -2201,7 +2191,8 @@ QemuConsole *graphic_console_init(DeviceState *dev, uint32_t head,
         height = qemu_console_get_height(s, 0);
     } else {
         trace_console_gfx_new();
-        s = new_console(TYPE_QEMU_GRAPHIC_CONSOLE, head);
+        s = (QemuConsole *)object_new(TYPE_QEMU_GRAPHIC_CONSOLE);
+        s->head = head;
         s->ui_timer = timer_new_ms(QEMU_CLOCK_REALTIME,
                                    dpy_set_ui_info_timer, s);
     }
@@ -2578,9 +2569,9 @@ static void vc_chr_open(Chardev *chr,
 
     trace_console_txt_new(width, height);
     if (width == 0 || height == 0) {
-        s = new_console(TYPE_QEMU_TEXT_CONSOLE, 0);
+        s = (QemuConsole *)object_new(TYPE_QEMU_TEXT_CONSOLE);
     } else {
-        s = new_console(TYPE_QEMU_FIXED_TEXT_CONSOLE, 0);
+        s = (QemuConsole *)object_new(TYPE_QEMU_FIXED_TEXT_CONSOLE);
         s->scanout.kind = SCANOUT_SURFACE;
         s->surface = qemu_create_displaysurface(width, height);
     }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 23/52] ui/console: specialize console_lookup_unused()
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (21 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 22/52] ui/console: remove new_console() marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 24/52] ui/console: update the head from unused QemuConsole marcandre.lureau
                   ` (29 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

graphics_console_init() is expected to return a graphic console.

The function doesn't need to be exported.

We are going to specialize further QemuGraphicConsole & QemuTextConsole.
The two will not be interchangeable anymore.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-24-marcandre.lureau@redhat.com>
---
 include/ui/console.h | 1 -
 ui/console.c         | 7 ++++---
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/include/ui/console.h b/include/ui/console.h
index 1b08b0f8ad..465f0f93a0 100644
--- a/include/ui/console.h
+++ b/include/ui/console.h
@@ -484,7 +484,6 @@ QemuConsole *qemu_console_lookup_by_index(unsigned int index);
 QemuConsole *qemu_console_lookup_by_device(DeviceState *dev, uint32_t head);
 QemuConsole *qemu_console_lookup_by_device_name(const char *device_id,
                                                 uint32_t head, Error **errp);
-QemuConsole *qemu_console_lookup_unused(void);
 QEMUCursor *qemu_console_get_cursor(QemuConsole *con);
 bool qemu_console_is_visible(QemuConsole *con);
 bool qemu_console_is_graphic(QemuConsole *con);
diff --git a/ui/console.c b/ui/console.c
index e0e4f980d7..08bed58b80 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -196,6 +196,7 @@ static void text_console_update_cursor(void *opaque);
 static bool displaychangelistener_has_dmabuf(DisplayChangeListener *dcl);
 static bool console_compatible_with(QemuConsole *con,
                                     DisplayChangeListener *dcl, Error **errp);
+static QemuConsole *qemu_graphic_console_lookup_unused(void);
 
 static void gui_update(void *opaque)
 {
@@ -2184,7 +2185,7 @@ QemuConsole *graphic_console_init(DeviceState *dev, uint32_t head,
     QemuConsole *s;
     DisplaySurface *surface;
 
-    s = qemu_console_lookup_unused();
+    s = qemu_graphic_console_lookup_unused();
     if (s) {
         trace_console_gfx_reuse(s->index);
         width = qemu_console_get_width(s, 0);
@@ -2289,13 +2290,13 @@ QemuConsole *qemu_console_lookup_by_device_name(const char *device_id,
     return con;
 }
 
-QemuConsole *qemu_console_lookup_unused(void)
+static QemuConsole *qemu_graphic_console_lookup_unused(void)
 {
     QemuConsole *con;
     Object *obj;
 
     QTAILQ_FOREACH(con, &consoles, next) {
-        if (con->hw_ops != &unused_ops) {
+        if (!QEMU_IS_GRAPHIC_CONSOLE(con) || con->hw_ops != &unused_ops) {
             continue;
         }
         obj = object_property_get_link(OBJECT(con),
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 24/52] ui/console: update the head from unused QemuConsole
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (22 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 23/52] ui/console: specialize console_lookup_unused() marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 25/52] ui/console: allocate ui_timer in QemuConsole marcandre.lureau
                   ` (28 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

When recycling unused QemuConsole, we should still set the associated
head number for correct information and lookups.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-25-marcandre.lureau@redhat.com>
---
 ui/console.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/ui/console.c b/ui/console.c
index 08bed58b80..a9a922b6e3 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -2193,10 +2193,10 @@ QemuConsole *graphic_console_init(DeviceState *dev, uint32_t head,
     } else {
         trace_console_gfx_new();
         s = (QemuConsole *)object_new(TYPE_QEMU_GRAPHIC_CONSOLE);
-        s->head = head;
         s->ui_timer = timer_new_ms(QEMU_CLOCK_REALTIME,
                                    dpy_set_ui_info_timer, s);
     }
+    s->head = head;
     graphic_console_set_hwops(s, hw_ops, opaque);
     if (dev) {
         object_property_set_link(OBJECT(s), "device", OBJECT(dev),
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 25/52] ui/console: allocate ui_timer in QemuConsole
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (23 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 24/52] ui/console: update the head from unused QemuConsole marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 26/52] ui/vc: move cursor_timer initialization to QemuTextConsole class marcandre.lureau
                   ` (27 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Although at this point only QemuGraphicConsole have hw_ops that
implements ui_info() callback, it makes sense to keep the code in the
base QemuConsole, to simplify conditions for the caller.

As of now, the code didn't reach a NULL timer because dpy_set_ui_info()
checks if dpy_ui_info_supported() (hw_ops->ui_info != NULL), which is
false for text_console_ops. This is a bit fragile, let simply allocate
and free the timer in the base class.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-26-marcandre.lureau@redhat.com>
---
 ui/console.c | 8 ++++++--
 1 file changed, 6 insertions(+), 2 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index a9a922b6e3..8c4a2c83fa 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -197,6 +197,7 @@ static bool displaychangelistener_has_dmabuf(DisplayChangeListener *dcl);
 static bool console_compatible_with(QemuConsole *con,
                                     DisplayChangeListener *dcl, Error **errp);
 static QemuConsole *qemu_graphic_console_lookup_unused(void);
+static void dpy_set_ui_info_timer(void *opaque);
 
 static void gui_update(void *opaque)
 {
@@ -1334,6 +1335,9 @@ qemu_console_register(QemuConsole *c)
 static void
 qemu_console_finalize(Object *obj)
 {
+    QemuConsole *c = QEMU_CONSOLE(obj);
+
+    g_clear_pointer(&c->ui_timer, timer_free);
     /* TODO: should unregister from consoles and free itself  */
 }
 
@@ -1367,6 +1371,8 @@ qemu_console_init(Object *obj)
     qemu_co_queue_init(&c->dump_queue);
     c->ds = ds;
     c->window_id = -1;
+    c->ui_timer = timer_new_ms(QEMU_CLOCK_REALTIME,
+                               dpy_set_ui_info_timer, c);
     qemu_console_register(c);
 }
 
@@ -2193,8 +2199,6 @@ QemuConsole *graphic_console_init(DeviceState *dev, uint32_t head,
     } else {
         trace_console_gfx_new();
         s = (QemuConsole *)object_new(TYPE_QEMU_GRAPHIC_CONSOLE);
-        s->ui_timer = timer_new_ms(QEMU_CLOCK_REALTIME,
-                                   dpy_set_ui_info_timer, s);
     }
     s->head = head;
     graphic_console_set_hwops(s, hw_ops, opaque);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 26/52] ui/vc: move cursor_timer initialization to QemuTextConsole class
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (24 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 25/52] ui/console: allocate ui_timer in QemuConsole marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 27/52] ui/console: free more QemuConsole resources marcandre.lureau
                   ` (26 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

The timer is only relevant when a text console exists.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-27-marcandre.lureau@redhat.com>
---
 ui/console.c | 6 ++++--
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 8c4a2c83fa..ffa68c3a22 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1399,6 +1399,10 @@ qemu_text_console_finalize(Object *obj)
 static void
 qemu_text_console_class_init(ObjectClass *oc, void *data)
 {
+    if (!cursor_timer) {
+        cursor_timer = timer_new_ms(QEMU_CLOCK_REALTIME,
+                                    text_console_update_cursor, NULL);
+    }
 }
 
 static void
@@ -2144,8 +2148,6 @@ static DisplayState *get_alloc_displaystate(void)
 {
     if (!display_state) {
         display_state = g_new0(DisplayState, 1);
-        cursor_timer = timer_new_ms(QEMU_CLOCK_REALTIME,
-                                    text_console_update_cursor, NULL);
     }
     return display_state;
 }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 27/52] ui/console: free more QemuConsole resources
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (25 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 26/52] ui/vc: move cursor_timer initialization to QemuTextConsole class marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 28/52] ui/vc: move text fields to QemuTextConsole marcandre.lureau
                   ` (25 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

This code path is probably not executed at this point, since console
aren't being released.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-28-marcandre.lureau@redhat.com>
---
 ui/console.c | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/ui/console.c b/ui/console.c
index ffa68c3a22..3cd4c74eec 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1337,8 +1337,11 @@ qemu_console_finalize(Object *obj)
 {
     QemuConsole *c = QEMU_CONSOLE(obj);
 
+    /* TODO: check this code path, and unregister from consoles */
+    g_clear_pointer(&c->device, object_unref);
+    g_clear_pointer(&c->surface, qemu_free_displaysurface);
+    g_clear_pointer(&c->gl_unblock_timer, timer_free);
     g_clear_pointer(&c->ui_timer, timer_free);
-    /* TODO: should unregister from consoles and free itself  */
 }
 
 static void
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 28/52] ui/vc: move text fields to QemuTextConsole
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (26 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 27/52] ui/console: free more QemuConsole resources marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 29/52] ui/console: move graphic fields to QemuGraphicConsole marcandre.lureau
                   ` (24 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Now we can instantiate the specific console with its own fields. Pass
the most appropriate type to the various functions, and cast up to
QEMU_CONSOLE as necessary.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-29-marcandre.lureau@redhat.com>
---
 ui/console.c | 177 ++++++++++++++++++++++++++-------------------------
 1 file changed, 91 insertions(+), 86 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 3cd4c74eec..335d7ba841 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -94,26 +94,6 @@ struct QemuConsole {
     const GraphicHwOps *hw_ops;
     void *hw;
 
-    /* Text console state */
-    int width;
-    int height;
-    int total_height;
-    int backscroll_height;
-    int x, y;
-    int y_displayed;
-    int y_base;
-    TextCell *cells;
-    int text_x[2], text_y[2], cursor_invalidate;
-    int echo;
-
-    int update_x0;
-    int update_y0;
-    int update_x1;
-    int update_y1;
-
-    Chardev *chr;
-    /* fifo for key pressed */
-    Fifo8 out_fifo;
     CoQueue dump_queue;
 
     QTAILQ_ENTRY(QemuConsole) next;
@@ -136,6 +116,26 @@ OBJECT_DEFINE_TYPE(QemuGraphicConsole, qemu_graphic_console, QEMU_GRAPHIC_CONSOL
 
 typedef struct QemuTextConsole {
     QemuConsole parent;
+
+    int width;
+    int height;
+    int total_height;
+    int backscroll_height;
+    int x, y;
+    int y_displayed;
+    int y_base;
+    TextCell *cells;
+    int text_x[2], text_y[2], cursor_invalidate;
+    int echo;
+
+    int update_x0;
+    int update_y0;
+    int update_x1;
+    int update_y1;
+
+    Chardev *chr;
+    /* fifo for key pressed */
+    Fifo8 out_fifo;
 } QemuTextConsole;
 
 typedef QemuConsoleClass QemuTextConsoleClass;
@@ -162,7 +162,7 @@ OBJECT_DEFINE_TYPE(QemuFixedTextConsole, qemu_fixed_text_console, QEMU_FIXED_TEX
 
 struct VCChardev {
     Chardev parent;
-    QemuConsole *console;
+    QemuTextConsole *console;
 
     enum TTYState state;
     int esc_params[MAX_ESC_PARAMS];
@@ -428,43 +428,44 @@ static void vga_putcharxy(QemuConsole *s, int x, int y, int ch,
                              &fgcol, &bgcol, x, y, FONT_WIDTH, FONT_HEIGHT);
 }
 
-static void text_console_resize(QemuConsole *s)
+static void text_console_resize(QemuTextConsole *t)
 {
+    QemuConsole *s = QEMU_CONSOLE(t);
     TextCell *cells, *c, *c1;
     int w1, x, y, last_width;
 
     assert(s->scanout.kind == SCANOUT_SURFACE);
 
-    last_width = s->width;
-    s->width = surface_width(s->surface) / FONT_WIDTH;
-    s->height = surface_height(s->surface) / FONT_HEIGHT;
+    last_width = t->width;
+    t->width = surface_width(s->surface) / FONT_WIDTH;
+    t->height = surface_height(s->surface) / FONT_HEIGHT;
 
     w1 = last_width;
-    if (s->width < w1)
-        w1 = s->width;
+    if (t->width < w1)
+        w1 = t->width;
 
-    cells = g_new(TextCell, s->width * s->total_height + 1);
-    for(y = 0; y < s->total_height; y++) {
-        c = &cells[y * s->width];
+    cells = g_new(TextCell, t->width * t->total_height + 1);
+    for(y = 0; y < t->total_height; y++) {
+        c = &cells[y * t->width];
         if (w1 > 0) {
-            c1 = &s->cells[y * last_width];
+            c1 = &t->cells[y * last_width];
             for(x = 0; x < w1; x++) {
                 *c++ = *c1++;
             }
         }
-        for(x = w1; x < s->width; x++) {
+        for(x = w1; x < t->width; x++) {
             c->ch = ' ';
             c->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
             c++;
         }
     }
-    g_free(s->cells);
-    s->cells = cells;
+    g_free(t->cells);
+    t->cells = cells;
 }
 
-static void invalidate_xy(QemuConsole *s, int x, int y)
+static void invalidate_xy(QemuTextConsole *s, int x, int y)
 {
-    if (!qemu_console_is_visible(s)) {
+    if (!qemu_console_is_visible(QEMU_CONSOLE(s))) {
         return;
     }
     if (s->update_x0 > x * FONT_WIDTH)
@@ -479,7 +480,7 @@ static void invalidate_xy(QemuConsole *s, int x, int y)
 
 static void vc_update_xy(VCChardev *vc, int x, int y)
 {
-    QemuConsole *s = vc->console;
+    QemuTextConsole *s = vc->console;
     TextCell *c;
     int y1, y2;
 
@@ -498,13 +499,13 @@ static void vc_update_xy(VCChardev *vc, int x, int y)
             x = s->width - 1;
         }
         c = &s->cells[y1 * s->width + x];
-        vga_putcharxy(s, x, y2, c->ch,
+        vga_putcharxy(QEMU_CONSOLE(s), x, y2, c->ch,
                       &(c->t_attrib));
         invalidate_xy(s, x, y2);
     }
 }
 
-static void console_show_cursor(QemuConsole *s, int show)
+static void console_show_cursor(QemuTextConsole *s, int show)
 {
     TextCell *c;
     int y, y1;
@@ -525,17 +526,17 @@ static void console_show_cursor(QemuConsole *s, int show)
         if (show && cursor_visible_phase) {
             TextAttributes t_attrib = TEXT_ATTRIBUTES_DEFAULT;
             t_attrib.invers = !(t_attrib.invers); /* invert fg and bg */
-            vga_putcharxy(s, x, y, c->ch, &t_attrib);
+            vga_putcharxy(QEMU_CONSOLE(s), x, y, c->ch, &t_attrib);
         } else {
-            vga_putcharxy(s, x, y, c->ch, &(c->t_attrib));
+            vga_putcharxy(QEMU_CONSOLE(s), x, y, c->ch, &(c->t_attrib));
         }
         invalidate_xy(s, x, y);
     }
 }
 
-static void console_refresh(QemuConsole *s)
+static void console_refresh(QemuTextConsole *s)
 {
-    DisplaySurface *surface = qemu_console_surface(s);
+    DisplaySurface *surface = qemu_console_surface(QEMU_CONSOLE(s));
     TextCell *c;
     int x, y, y1;
 
@@ -545,13 +546,13 @@ static void console_refresh(QemuConsole *s)
     s->text_y[1] = s->height - 1;
     s->cursor_invalidate = 1;
 
-    vga_fill_rect(s, 0, 0, surface_width(surface), surface_height(surface),
+    vga_fill_rect(QEMU_CONSOLE(s), 0, 0, surface_width(surface), surface_height(surface),
                   color_table_rgb[0][QEMU_COLOR_BLACK]);
     y1 = s->y_displayed;
     for (y = 0; y < s->height; y++) {
         c = s->cells + y1 * s->width;
         for (x = 0; x < s->width; x++) {
-            vga_putcharxy(s, x, y, c->ch,
+            vga_putcharxy(QEMU_CONSOLE(s), x, y, c->ch,
                           &(c->t_attrib));
             c++;
         }
@@ -560,11 +561,11 @@ static void console_refresh(QemuConsole *s)
         }
     }
     console_show_cursor(s, 1);
-    dpy_gfx_update(s, 0, 0,
+    dpy_gfx_update(QEMU_CONSOLE(s), 0, 0,
                    surface_width(surface), surface_height(surface));
 }
 
-static void console_scroll(QemuConsole *s, int ydelta)
+static void console_scroll(QemuTextConsole *s, int ydelta)
 {
     int i, y1;
 
@@ -595,7 +596,7 @@ static void console_scroll(QemuConsole *s, int ydelta)
 
 static void vc_put_lf(VCChardev *vc)
 {
-    QemuConsole *s = vc->console;
+    QemuTextConsole *s = vc->console;
     TextCell *c;
     int x, y1;
 
@@ -624,10 +625,10 @@ static void vc_put_lf(VCChardev *vc)
             s->text_x[1] = s->width - 1;
             s->text_y[1] = s->height - 1;
 
-            vga_bitblt(s, 0, FONT_HEIGHT, 0, 0,
+            vga_bitblt(QEMU_CONSOLE(s), 0, FONT_HEIGHT, 0, 0,
                        s->width * FONT_WIDTH,
                        (s->height - 1) * FONT_HEIGHT);
-            vga_fill_rect(s, 0, (s->height - 1) * FONT_HEIGHT,
+            vga_fill_rect(QEMU_CONSOLE(s), 0, (s->height - 1) * FONT_HEIGHT,
                           s->width * FONT_WIDTH, FONT_HEIGHT,
                           color_table_rgb[0][TEXT_ATTRIBUTES_DEFAULT.bgcol]);
             s->update_x0 = 0;
@@ -737,7 +738,7 @@ static void vc_handle_escape(VCChardev *vc)
 
 static void vc_clear_xy(VCChardev *vc, int x, int y)
 {
-    QemuConsole *s = vc->console;
+    QemuTextConsole *s = vc->console;
     int y1 = (s->y_base + y) % s->total_height;
     if (x >= s->width) {
         x = s->width - 1;
@@ -750,7 +751,7 @@ static void vc_clear_xy(VCChardev *vc, int x, int y)
 
 static void vc_put_one(VCChardev *vc, int ch)
 {
-    QemuConsole *s = vc->console;
+    QemuTextConsole *s = vc->console;
     TextCell *c;
     int y1;
     if (s->x >= s->width) {
@@ -777,7 +778,7 @@ static void vc_respond_str(VCChardev *vc, const char *buf)
 /* set cursor, checking bounds */
 static void vc_set_cursor(VCChardev *vc, int x, int y)
 {
-    QemuConsole *s = vc->console;
+    QemuTextConsole *s = vc->console;
 
     if (x < 0) {
         x = 0;
@@ -798,7 +799,7 @@ static void vc_set_cursor(VCChardev *vc, int x, int y)
 
 static void vc_putchar(VCChardev *vc, int ch)
 {
-    QemuConsole *s = vc->console;
+    QemuTextConsole *s = vc->console;
     int i;
     int x, y;
     char response[40];
@@ -1095,8 +1096,11 @@ void console_select(unsigned int index)
             }
             displaychangelistener_display_console(dcl, s, NULL);
         }
-        dpy_text_resize(s, s->width, s->height);
-        text_console_update_cursor(NULL);
+
+        if (QEMU_IS_TEXT_CONSOLE(s)) {
+            dpy_text_resize(s, QEMU_TEXT_CONSOLE(s)->width, QEMU_TEXT_CONSOLE(s)->height);
+            text_console_update_cursor(NULL);
+        }
     }
 }
 
@@ -1107,7 +1111,7 @@ DECLARE_INSTANCE_CHECKER(VCChardev, VC_CHARDEV,
 static int vc_chr_write(Chardev *chr, const uint8_t *buf, int len)
 {
     VCChardev *drv = VC_CHARDEV(chr);
-    QemuConsole *s = drv->console;
+    QemuTextConsole *s = drv->console;
     int i;
 
     s->update_x0 = s->width * FONT_WIDTH;
@@ -1120,14 +1124,14 @@ static int vc_chr_write(Chardev *chr, const uint8_t *buf, int len)
     }
     console_show_cursor(s, 1);
     if (s->update_x0 < s->update_x1) {
-        dpy_gfx_update(s, s->update_x0, s->update_y0,
+        dpy_gfx_update(QEMU_CONSOLE(s), s->update_x0, s->update_y0,
                        s->update_x1 - s->update_x0,
                        s->update_y1 - s->update_y0);
     }
     return len;
 }
 
-static void kbd_send_chars(QemuConsole *s)
+static void kbd_send_chars(QemuTextConsole *s)
 {
     uint32_t len, avail;
 
@@ -1145,13 +1149,14 @@ static void kbd_send_chars(QemuConsole *s)
 }
 
 /* called when an ascii key is pressed */
-void kbd_put_keysym_console(QemuConsole *s, int keysym)
+void kbd_put_keysym_console(QemuConsole *con, int keysym)
 {
+    QemuTextConsole *s = (QemuTextConsole *)object_dynamic_cast(OBJECT(con), TYPE_QEMU_TEXT_CONSOLE);
     uint8_t buf[16], *q;
     int c;
     uint32_t num_free;
 
-    if (!s || QEMU_IS_GRAPHIC_CONSOLE(s))
+    if (!s)
         return;
 
     switch(keysym) {
@@ -1251,17 +1256,17 @@ void kbd_put_keysym(int keysym)
 
 static void text_console_invalidate(void *opaque)
 {
-    QemuConsole *s = (QemuConsole *) opaque;
+    QemuTextConsole *s = QEMU_TEXT_CONSOLE(opaque);
 
-    if (QEMU_IS_TEXT_CONSOLE(s) && !QEMU_IS_FIXED_TEXT_CONSOLE(s)) {
-        text_console_resize(s);
+    if (!QEMU_IS_FIXED_TEXT_CONSOLE(s)) {
+        text_console_resize(QEMU_TEXT_CONSOLE(s));
     }
     console_refresh(s);
 }
 
 static void text_console_update(void *opaque, console_ch_t *chardata)
 {
-    QemuConsole *s = (QemuConsole *) opaque;
+    QemuTextConsole *s = QEMU_TEXT_CONSOLE(opaque);
     int i, j, src;
 
     if (s->text_x[0] <= s->text_x[1]) {
@@ -1275,7 +1280,7 @@ static void text_console_update(void *opaque, console_ch_t *chardata)
                                              s->cells[src].t_attrib.bgcol,
                                              s->cells[src].t_attrib.bold));
             }
-        dpy_text_update(s, s->text_x[0], s->text_y[0],
+        dpy_text_update(QEMU_CONSOLE(s), s->text_x[0], s->text_y[0],
                         s->text_x[1] - s->text_x[0], i - s->text_y[0]);
         s->text_x[0] = s->width;
         s->text_y[0] = s->height;
@@ -1283,7 +1288,7 @@ static void text_console_update(void *opaque, console_ch_t *chardata)
         s->text_y[1] = 0;
     }
     if (s->cursor_invalidate) {
-        dpy_text_cursor(s, s->x, s->y);
+        dpy_text_cursor(QEMU_CONSOLE(s), s->x, s->y);
         s->cursor_invalidate = 0;
     }
 }
@@ -2399,12 +2404,14 @@ char *qemu_console_get_label(QemuConsole *con)
             }
         }
         return g_strdup("VGA");
-    } else {
-        if (con->chr && con->chr->label) {
-            return g_strdup(con->chr->label);
+    } else if (QEMU_IS_TEXT_CONSOLE(con)) {
+        QemuTextConsole *c = QEMU_TEXT_CONSOLE(con);
+        if (c->chr && c->chr->label) {
+            return g_strdup(c->chr->label);
         }
-        return g_strdup_printf("vc%d", con->index);
     }
+
+    return g_strdup_printf("vc%d", con->index);
 }
 
 int qemu_console_get_index(QemuConsole *con)
@@ -2466,17 +2473,15 @@ int qemu_console_get_height(QemuConsole *con, int fallback)
 static void vc_chr_accept_input(Chardev *chr)
 {
     VCChardev *drv = VC_CHARDEV(chr);
-    QemuConsole *s = drv->console;
 
-    kbd_send_chars(s);
+    kbd_send_chars(drv->console);
 }
 
 static void vc_chr_set_echo(Chardev *chr, bool echo)
 {
     VCChardev *drv = VC_CHARDEV(chr);
-    QemuConsole *s = drv->console;
 
-    s->echo = echo;
+    drv->console->echo = echo;
 }
 
 static void text_console_update_cursor_timer(void)
@@ -2514,7 +2519,7 @@ static const GraphicHwOps text_console_ops = {
 static void text_console_do_init(Chardev *chr)
 {
     VCChardev *drv = VC_CHARDEV(chr);
-    QemuConsole *s = drv->console;
+    QemuTextConsole *s = drv->console;
     int g_width = 80 * FONT_WIDTH;
     int g_height = 24 * FONT_HEIGHT;
 
@@ -2525,17 +2530,17 @@ static void text_console_do_init(Chardev *chr)
     s->total_height = DEFAULT_BACKSCROLL;
     s->x = 0;
     s->y = 0;
-    if (s->scanout.kind != SCANOUT_SURFACE) {
+    if (QEMU_CONSOLE(s)->scanout.kind != SCANOUT_SURFACE) {
         if (active_console && active_console->scanout.kind == SCANOUT_SURFACE) {
             g_width = qemu_console_get_width(active_console, g_width);
             g_height = qemu_console_get_height(active_console, g_height);
         }
-        s->surface = qemu_create_displaysurface(g_width, g_height);
-        s->scanout.kind = SCANOUT_SURFACE;
+        QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(g_width, g_height);
+        QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
     }
 
-    s->hw_ops = &text_console_ops;
-    s->hw = s;
+    QEMU_CONSOLE(s)->hw_ops = &text_console_ops;
+    QEMU_CONSOLE(s)->hw = s;
 
     /* set current text attributes to default */
     drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
@@ -2561,7 +2566,7 @@ static void vc_chr_open(Chardev *chr,
 {
     ChardevVC *vc = backend->u.vc.data;
     VCChardev *drv = VC_CHARDEV(chr);
-    QemuConsole *s;
+    QemuTextConsole *s;
     unsigned width = 0;
     unsigned height = 0;
 
@@ -2579,11 +2584,11 @@ static void vc_chr_open(Chardev *chr,
 
     trace_console_txt_new(width, height);
     if (width == 0 || height == 0) {
-        s = (QemuConsole *)object_new(TYPE_QEMU_TEXT_CONSOLE);
+        s = QEMU_TEXT_CONSOLE(object_new(TYPE_QEMU_TEXT_CONSOLE));
     } else {
-        s = (QemuConsole *)object_new(TYPE_QEMU_FIXED_TEXT_CONSOLE);
-        s->scanout.kind = SCANOUT_SURFACE;
-        s->surface = qemu_create_displaysurface(width, height);
+        s = QEMU_TEXT_CONSOLE(object_new(TYPE_QEMU_FIXED_TEXT_CONSOLE));
+        QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
+        QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(width, height);
     }
 
     s->chr = chr;
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 29/52] ui/console: move graphic fields to QemuGraphicConsole
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (27 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 28/52] ui/vc: move text fields to QemuTextConsole marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 30/52] ui/vc: fold text_console_do_init() in vc_chr_open() marcandre.lureau
                   ` (23 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Move fields specific to graphic console to the console subclass.

qemu_console_get_head() is adapated to accomodate QemuTextConsole, and
always returns 0.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-30-marcandre.lureau@redhat.com>
---
 ui/console.c | 110 ++++++++++++++++++++++++++++++---------------------
 1 file changed, 64 insertions(+), 46 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 335d7ba841..9d884ba02f 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -83,17 +83,10 @@ struct QemuConsole {
     int gl_block;
     QEMUTimer *gl_unblock_timer;
     int window_id;
-
-    /* Graphic console state.  */
-    Object *device;
-    uint32_t head;
     QemuUIInfo ui_info;
     QEMUTimer *ui_timer;
-    QEMUCursor *cursor;
-    int cursor_x, cursor_y, cursor_on;
     const GraphicHwOps *hw_ops;
     void *hw;
-
     CoQueue dump_queue;
 
     QTAILQ_ENTRY(QemuConsole) next;
@@ -103,6 +96,12 @@ OBJECT_DEFINE_ABSTRACT_TYPE(QemuConsole, qemu_console, QEMU_CONSOLE, OBJECT)
 
 typedef struct QemuGraphicConsole {
     QemuConsole parent;
+
+    Object *device;
+    uint32_t head;
+
+    QEMUCursor *cursor;
+    int cursor_x, cursor_y, cursor_on;
 } QemuGraphicConsole;
 
 typedef QemuConsoleClass QemuGraphicConsoleClass;
@@ -1343,31 +1342,14 @@ qemu_console_finalize(Object *obj)
     QemuConsole *c = QEMU_CONSOLE(obj);
 
     /* TODO: check this code path, and unregister from consoles */
-    g_clear_pointer(&c->device, object_unref);
     g_clear_pointer(&c->surface, qemu_free_displaysurface);
     g_clear_pointer(&c->gl_unblock_timer, timer_free);
     g_clear_pointer(&c->ui_timer, timer_free);
 }
 
-static void
-qemu_console_prop_get_head(Object *obj, Visitor *v, const char *name,
-                           void *opaque, Error **errp)
-{
-    QemuConsole *c = QEMU_CONSOLE(obj);
-
-    visit_type_uint32(v, name, &c->head, errp);
-}
-
 static void
 qemu_console_class_init(ObjectClass *oc, void *data)
 {
-    object_class_property_add_link(oc, "device", TYPE_DEVICE,
-                                   offsetof(QemuConsole, device),
-                                   object_property_allow_set_link,
-                                   OBJ_PROP_LINK_STRONG);
-    object_class_property_add(oc, "head", "uint32",
-                              qemu_console_prop_get_head,
-                              NULL, NULL, NULL);
 }
 
 static void
@@ -1387,11 +1369,30 @@ qemu_console_init(Object *obj)
 static void
 qemu_graphic_console_finalize(Object *obj)
 {
+    QemuGraphicConsole *c = QEMU_GRAPHIC_CONSOLE(obj);
+
+    g_clear_pointer(&c->device, object_unref);
+}
+
+static void
+qemu_graphic_console_prop_get_head(Object *obj, Visitor *v, const char *name,
+                                   void *opaque, Error **errp)
+{
+    QemuGraphicConsole *c = QEMU_GRAPHIC_CONSOLE(obj);
+
+    visit_type_uint32(v, name, &c->head, errp);
 }
 
 static void
 qemu_graphic_console_class_init(ObjectClass *oc, void *data)
 {
+    object_class_property_add_link(oc, "device", TYPE_DEVICE,
+                                   offsetof(QemuGraphicConsole, device),
+                                   object_property_allow_set_link,
+                                   OBJ_PROP_LINK_STRONG);
+    object_class_property_add(oc, "head", "uint32",
+                              qemu_graphic_console_prop_get_head,
+                              NULL, NULL, NULL);
 }
 
 static void
@@ -1676,6 +1677,16 @@ void qemu_console_set_display_gl_ctx(QemuConsole *con, DisplayGLCtx *gl)
     con->gl = gl;
 }
 
+static void
+dcl_set_graphic_cursor(DisplayChangeListener *dcl, QemuGraphicConsole *con)
+{
+    if (con && con->cursor && dcl->ops->dpy_cursor_define) {
+        dcl->ops->dpy_cursor_define(dcl, con->cursor);
+    }
+    if (con && dcl->ops->dpy_mouse_set) {
+        dcl->ops->dpy_mouse_set(dcl, con->cursor_x, con->cursor_y, con->cursor_on);
+    }
+}
 void register_displaychangelistener(DisplayChangeListener *dcl)
 {
     QemuConsole *con;
@@ -1693,11 +1704,8 @@ void register_displaychangelistener(DisplayChangeListener *dcl)
         con = active_console;
     }
     displaychangelistener_display_console(dcl, con, dcl->con ? &error_fatal : NULL);
-    if (con && con->cursor && dcl->ops->dpy_cursor_define) {
-        dcl->ops->dpy_cursor_define(dcl, con->cursor);
-    }
-    if (con && dcl->ops->dpy_mouse_set) {
-        dcl->ops->dpy_mouse_set(dcl, con->cursor_x, con->cursor_y, con->cursor_on);
+    if (QEMU_IS_GRAPHIC_CONSOLE(con)) {
+        dcl_set_graphic_cursor(dcl, QEMU_GRAPHIC_CONSOLE(con));
     }
     text_console_update_cursor(NULL);
 }
@@ -1728,8 +1736,9 @@ void unregister_displaychangelistener(DisplayChangeListener *dcl)
 static void dpy_set_ui_info_timer(void *opaque)
 {
     QemuConsole *con = opaque;
+    uint32_t head = qemu_console_get_head(con);
 
-    con->hw_ops->ui_info(con->hw, con->head, &con->ui_info);
+    con->hw_ops->ui_info(con->hw, head, &con->ui_info);
 }
 
 bool dpy_ui_info_supported(QemuConsole *con)
@@ -1939,19 +1948,20 @@ void dpy_text_resize(QemuConsole *con, int w, int h)
     }
 }
 
-void dpy_mouse_set(QemuConsole *con, int x, int y, int on)
+void dpy_mouse_set(QemuConsole *c, int x, int y, int on)
 {
-    DisplayState *s = con->ds;
+    QemuGraphicConsole *con = QEMU_GRAPHIC_CONSOLE(c);
+    DisplayState *s = c->ds;
     DisplayChangeListener *dcl;
 
     con->cursor_x = x;
     con->cursor_y = y;
     con->cursor_on = on;
-    if (!qemu_console_is_visible(con)) {
+    if (!qemu_console_is_visible(c)) {
         return;
     }
     QLIST_FOREACH(dcl, &s->listeners, next) {
-        if (con != (dcl->con ? dcl->con : active_console)) {
+        if (c != (dcl->con ? dcl->con : active_console)) {
             continue;
         }
         if (dcl->ops->dpy_mouse_set) {
@@ -1960,18 +1970,19 @@ void dpy_mouse_set(QemuConsole *con, int x, int y, int on)
     }
 }
 
-void dpy_cursor_define(QemuConsole *con, QEMUCursor *cursor)
+void dpy_cursor_define(QemuConsole *c, QEMUCursor *cursor)
 {
-    DisplayState *s = con->ds;
+    QemuGraphicConsole *con = QEMU_GRAPHIC_CONSOLE(c);
+    DisplayState *s = c->ds;
     DisplayChangeListener *dcl;
 
     cursor_unref(con->cursor);
     con->cursor = cursor_ref(cursor);
-    if (!qemu_console_is_visible(con)) {
+    if (!qemu_console_is_visible(c)) {
         return;
     }
     QLIST_FOREACH(dcl, &s->listeners, next) {
-        if (con != (dcl->con ? dcl->con : active_console)) {
+        if (c != (dcl->con ? dcl->con : active_console)) {
             continue;
         }
         if (dcl->ops->dpy_cursor_define) {
@@ -2210,7 +2221,7 @@ QemuConsole *graphic_console_init(DeviceState *dev, uint32_t head,
         trace_console_gfx_new();
         s = (QemuConsole *)object_new(TYPE_QEMU_GRAPHIC_CONSOLE);
     }
-    s->head = head;
+    QEMU_GRAPHIC_CONSOLE(s)->head = head;
     graphic_console_set_hwops(s, hw_ops, opaque);
     if (dev) {
         object_property_set_link(OBJECT(s), "device", OBJECT(dev),
@@ -2328,7 +2339,7 @@ QEMUCursor *qemu_console_get_cursor(QemuConsole *con)
     if (con == NULL) {
         con = active_console;
     }
-    return con ? con->cursor : NULL;
+    return QEMU_IS_GRAPHIC_CONSOLE(con) ? QEMU_GRAPHIC_CONSOLE(con)->cursor : NULL;
 }
 
 bool qemu_console_is_visible(QemuConsole *con)
@@ -2386,21 +2397,22 @@ bool qemu_console_is_multihead(DeviceState *dev)
 char *qemu_console_get_label(QemuConsole *con)
 {
     if (QEMU_IS_GRAPHIC_CONSOLE(con)) {
-        if (con->device) {
+        QemuGraphicConsole *c = QEMU_GRAPHIC_CONSOLE(con);
+        if (c->device) {
             DeviceState *dev;
             bool multihead;
 
-            dev = DEVICE(con->device);
+            dev = DEVICE(c->device);
             multihead = qemu_console_is_multihead(dev);
             if (multihead) {
                 return g_strdup_printf("%s.%d", dev->id ?
                                        dev->id :
-                                       object_get_typename(con->device),
-                                       con->head);
+                                       object_get_typename(c->device),
+                                       c->head);
             } else {
                 return g_strdup_printf("%s", dev->id ?
                                        dev->id :
-                                       object_get_typename(con->device));
+                                       object_get_typename(c->device));
             }
         }
         return g_strdup("VGA");
@@ -2427,7 +2439,13 @@ uint32_t qemu_console_get_head(QemuConsole *con)
     if (con == NULL) {
         con = active_console;
     }
-    return con ? con->head : -1;
+    if (con == NULL) {
+        return -1;
+    }
+    if (QEMU_IS_GRAPHIC_CONSOLE(con)) {
+        return QEMU_GRAPHIC_CONSOLE(con)->head;
+    }
+    return 0;
 }
 
 int qemu_console_get_width(QemuConsole *con, int fallback)
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 30/52] ui/vc: fold text_console_do_init() in vc_chr_open()
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (28 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 29/52] ui/console: move graphic fields to QemuGraphicConsole marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 31/52] ui/vc: move some text console initialization to qom handlers marcandre.lureau
                   ` (22 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Message-Id: <20230830093843.3531473-31-marcandre.lureau@redhat.com>
---
 ui/console.c | 80 ++++++++++++++++++++--------------------------------
 1 file changed, 31 insertions(+), 49 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 9d884ba02f..22505d093f 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -187,7 +187,6 @@ static QTAILQ_HEAD(, QemuConsole) consoles =
 static bool cursor_visible_phase;
 static QEMUTimer *cursor_timer;
 
-static void text_console_do_init(Chardev *chr);
 static void dpy_refresh(DisplayState *s);
 static DisplayState *get_alloc_displaystate(void);
 static void text_console_update_cursor_timer(void);
@@ -2534,49 +2533,6 @@ static const GraphicHwOps text_console_ops = {
     .text_update = text_console_update,
 };
 
-static void text_console_do_init(Chardev *chr)
-{
-    VCChardev *drv = VC_CHARDEV(chr);
-    QemuTextConsole *s = drv->console;
-    int g_width = 80 * FONT_WIDTH;
-    int g_height = 24 * FONT_HEIGHT;
-
-    fifo8_create(&s->out_fifo, 16);
-
-    s->y_displayed = 0;
-    s->y_base = 0;
-    s->total_height = DEFAULT_BACKSCROLL;
-    s->x = 0;
-    s->y = 0;
-    if (QEMU_CONSOLE(s)->scanout.kind != SCANOUT_SURFACE) {
-        if (active_console && active_console->scanout.kind == SCANOUT_SURFACE) {
-            g_width = qemu_console_get_width(active_console, g_width);
-            g_height = qemu_console_get_height(active_console, g_height);
-        }
-        QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(g_width, g_height);
-        QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
-    }
-
-    QEMU_CONSOLE(s)->hw_ops = &text_console_ops;
-    QEMU_CONSOLE(s)->hw = s;
-
-    /* set current text attributes to default */
-    drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
-    text_console_resize(s);
-
-    if (chr->label) {
-        char *msg;
-
-        drv->t_attrib.bgcol = QEMU_COLOR_BLUE;
-        msg = g_strdup_printf("%s console\r\n", chr->label);
-        qemu_chr_write(chr, (uint8_t *)msg, strlen(msg), true);
-        g_free(msg);
-        drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
-    }
-
-    qemu_chr_be_event(chr, CHR_EVENT_OPENED);
-}
-
 static void vc_chr_open(Chardev *chr,
                         ChardevBackend *backend,
                         bool *be_opened,
@@ -2587,6 +2543,8 @@ static void vc_chr_open(Chardev *chr,
     QemuTextConsole *s;
     unsigned width = 0;
     unsigned height = 0;
+    int g_width = 80 * FONT_WIDTH;
+    int g_height = 24 * FONT_HEIGHT;
 
     if (vc->has_width) {
         width = vc->width;
@@ -2612,12 +2570,36 @@ static void vc_chr_open(Chardev *chr,
     s->chr = chr;
     drv->console = s;
 
-    text_console_do_init(chr);
+    fifo8_create(&s->out_fifo, 16);
 
-    /* console/chardev init sometimes completes elsewhere in a 2nd
-     * stage, so defer OPENED events until they are fully initialized
-     */
-    *be_opened = false;
+    s->total_height = DEFAULT_BACKSCROLL;
+    if (QEMU_CONSOLE(s)->scanout.kind != SCANOUT_SURFACE) {
+        if (active_console && active_console->scanout.kind == SCANOUT_SURFACE) {
+            g_width = qemu_console_get_width(active_console, g_width);
+            g_height = qemu_console_get_height(active_console, g_height);
+        }
+        QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(g_width, g_height);
+        QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
+    }
+
+    QEMU_CONSOLE(s)->hw_ops = &text_console_ops;
+    QEMU_CONSOLE(s)->hw = s;
+
+    /* set current text attributes to default */
+    drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
+    text_console_resize(s);
+
+    if (chr->label) {
+        char *msg;
+
+        drv->t_attrib.bgcol = QEMU_COLOR_BLUE;
+        msg = g_strdup_printf("%s console\r\n", chr->label);
+        qemu_chr_write(chr, (uint8_t *)msg, strlen(msg), true);
+        g_free(msg);
+        drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
+    }
+
+    *be_opened = true;
 }
 
 void qemu_console_resize(QemuConsole *s, int width, int height)
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 31/52] ui/vc: move some text console initialization to qom handlers
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (29 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 30/52] ui/vc: fold text_console_do_init() in vc_chr_open() marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 32/52] ui/console: simplify getting active_console size marcandre.lureau
                   ` (21 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-32-marcandre.lureau@redhat.com>
---
 ui/console.c | 22 +++++++++++-----------
 1 file changed, 11 insertions(+), 11 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 22505d093f..5d521ba79d 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1413,9 +1413,20 @@ qemu_text_console_class_init(ObjectClass *oc, void *data)
     }
 }
 
+static const GraphicHwOps text_console_ops = {
+    .invalidate  = text_console_invalidate,
+    .text_update = text_console_update,
+};
+
 static void
 qemu_text_console_init(Object *obj)
 {
+    QemuTextConsole *c = QEMU_TEXT_CONSOLE(obj);
+
+    fifo8_create(&c->out_fifo, 16);
+    c->total_height = DEFAULT_BACKSCROLL;
+    QEMU_CONSOLE(c)->hw_ops = &text_console_ops;
+    QEMU_CONSOLE(c)->hw = c;
 }
 
 static void
@@ -2528,11 +2539,6 @@ static void text_console_update_cursor(void *opaque)
     }
 }
 
-static const GraphicHwOps text_console_ops = {
-    .invalidate  = text_console_invalidate,
-    .text_update = text_console_update,
-};
-
 static void vc_chr_open(Chardev *chr,
                         ChardevBackend *backend,
                         bool *be_opened,
@@ -2570,9 +2576,6 @@ static void vc_chr_open(Chardev *chr,
     s->chr = chr;
     drv->console = s;
 
-    fifo8_create(&s->out_fifo, 16);
-
-    s->total_height = DEFAULT_BACKSCROLL;
     if (QEMU_CONSOLE(s)->scanout.kind != SCANOUT_SURFACE) {
         if (active_console && active_console->scanout.kind == SCANOUT_SURFACE) {
             g_width = qemu_console_get_width(active_console, g_width);
@@ -2582,9 +2585,6 @@ static void vc_chr_open(Chardev *chr,
         QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
     }
 
-    QEMU_CONSOLE(s)->hw_ops = &text_console_ops;
-    QEMU_CONSOLE(s)->hw = s;
-
     /* set current text attributes to default */
     drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
     text_console_resize(s);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 32/52] ui/console: simplify getting active_console size
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (30 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 31/52] ui/vc: move some text console initialization to qom handlers marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 33/52] ui/console: remove need for g_width/g_height marcandre.lureau
                   ` (20 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

We can get the active console dimension regardless of its kind, by
simply giving NULL as argument. It will fallback with the given value
when the dimensions aren't known.

This will also allow to move the code in a separate unit more easily.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-33-marcandre.lureau@redhat.com>
---
 ui/console.c | 6 ++----
 1 file changed, 2 insertions(+), 4 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 5d521ba79d..70e11f924d 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -2577,10 +2577,8 @@ static void vc_chr_open(Chardev *chr,
     drv->console = s;
 
     if (QEMU_CONSOLE(s)->scanout.kind != SCANOUT_SURFACE) {
-        if (active_console && active_console->scanout.kind == SCANOUT_SURFACE) {
-            g_width = qemu_console_get_width(active_console, g_width);
-            g_height = qemu_console_get_height(active_console, g_height);
-        }
+        g_width = qemu_console_get_width(NULL, g_width);
+        g_height = qemu_console_get_height(NULL, g_height);
         QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(g_width, g_height);
         QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
     }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 33/52] ui/console: remove need for g_width/g_height
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (31 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 32/52] ui/console: simplify getting active_console size marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 34/52] ui/vc: use common text console surface creation marcandre.lureau
                   ` (19 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-34-marcandre.lureau@redhat.com>
---
 ui/console.c | 8 +++-----
 1 file changed, 3 insertions(+), 5 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 70e11f924d..a3fd1c5059 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -2549,8 +2549,6 @@ static void vc_chr_open(Chardev *chr,
     QemuTextConsole *s;
     unsigned width = 0;
     unsigned height = 0;
-    int g_width = 80 * FONT_WIDTH;
-    int g_height = 24 * FONT_HEIGHT;
 
     if (vc->has_width) {
         width = vc->width;
@@ -2567,6 +2565,8 @@ static void vc_chr_open(Chardev *chr,
     trace_console_txt_new(width, height);
     if (width == 0 || height == 0) {
         s = QEMU_TEXT_CONSOLE(object_new(TYPE_QEMU_TEXT_CONSOLE));
+        width = qemu_console_get_width(NULL, 80 * FONT_WIDTH);
+        height = qemu_console_get_height(NULL, 24 * FONT_HEIGHT);
     } else {
         s = QEMU_TEXT_CONSOLE(object_new(TYPE_QEMU_FIXED_TEXT_CONSOLE));
         QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
@@ -2577,9 +2577,7 @@ static void vc_chr_open(Chardev *chr,
     drv->console = s;
 
     if (QEMU_CONSOLE(s)->scanout.kind != SCANOUT_SURFACE) {
-        g_width = qemu_console_get_width(NULL, g_width);
-        g_height = qemu_console_get_height(NULL, g_height);
-        QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(g_width, g_height);
+        QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(width, height);
         QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
     }
 
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 34/52] ui/vc: use common text console surface creation
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (32 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 33/52] ui/console: remove need for g_width/g_height marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 35/52] ui/console: declare console types in console.h marcandre.lureau
                   ` (18 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-35-marcandre.lureau@redhat.com>
---
 ui/console.c | 9 ++-------
 1 file changed, 2 insertions(+), 7 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index a3fd1c5059..3d884956b7 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -2569,18 +2569,13 @@ static void vc_chr_open(Chardev *chr,
         height = qemu_console_get_height(NULL, 24 * FONT_HEIGHT);
     } else {
         s = QEMU_TEXT_CONSOLE(object_new(TYPE_QEMU_FIXED_TEXT_CONSOLE));
-        QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
-        QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(width, height);
     }
 
+    dpy_gfx_replace_surface(QEMU_CONSOLE(s), qemu_create_displaysurface(width, height));
+
     s->chr = chr;
     drv->console = s;
 
-    if (QEMU_CONSOLE(s)->scanout.kind != SCANOUT_SURFACE) {
-        QEMU_CONSOLE(s)->surface = qemu_create_displaysurface(width, height);
-        QEMU_CONSOLE(s)->scanout.kind = SCANOUT_SURFACE;
-    }
-
     /* set current text attributes to default */
     drv->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
     text_console_resize(s);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 35/52] ui/console: declare console types in console.h
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (33 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 34/52] ui/vc: use common text console surface creation marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 36/52] ui/console: use QEMU_PIXMAN_COLOR helpers marcandre.lureau
                   ` (17 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

We are going to split the console.c unit next, and implement
separately. But we need to check the underlying type in various places.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-36-marcandre.lureau@redhat.com>
---
 include/ui/console.h | 25 +++++++++++++++++++++----
 ui/console.c         | 15 ---------------
 2 files changed, 21 insertions(+), 19 deletions(-)

diff --git a/include/ui/console.h b/include/ui/console.h
index 465f0f93a0..0f7f50deaf 100644
--- a/include/ui/console.h
+++ b/include/ui/console.h
@@ -12,6 +12,27 @@
 # include "ui/shader.h"
 #endif
 
+#define TYPE_QEMU_CONSOLE "qemu-console"
+OBJECT_DECLARE_TYPE(QemuConsole, QemuConsoleClass, QEMU_CONSOLE)
+
+#define TYPE_QEMU_GRAPHIC_CONSOLE "qemu-graphic-console"
+OBJECT_DECLARE_SIMPLE_TYPE(QemuGraphicConsole, QEMU_GRAPHIC_CONSOLE)
+
+#define TYPE_QEMU_TEXT_CONSOLE "qemu-text-console"
+OBJECT_DECLARE_SIMPLE_TYPE(QemuTextConsole, QEMU_TEXT_CONSOLE)
+
+#define TYPE_QEMU_FIXED_TEXT_CONSOLE "qemu-fixed-text-console"
+OBJECT_DECLARE_SIMPLE_TYPE(QemuFixedTextConsole, QEMU_FIXED_TEXT_CONSOLE)
+
+#define QEMU_IS_GRAPHIC_CONSOLE(c) \
+    object_dynamic_cast(OBJECT(c), TYPE_QEMU_GRAPHIC_CONSOLE)
+
+#define QEMU_IS_TEXT_CONSOLE(c) \
+    object_dynamic_cast(OBJECT(c), TYPE_QEMU_TEXT_CONSOLE)
+
+#define QEMU_IS_FIXED_TEXT_CONSOLE(c) \
+    object_dynamic_cast(OBJECT(c), TYPE_QEMU_FIXED_TEXT_CONSOLE)
+
 /* keyboard/mouse support */
 
 #define MOUSE_EVENT_LBUTTON 0x01
@@ -112,10 +133,6 @@ void console_handle_touch_event(QemuConsole *con,
                                 Error **errp);
 /* consoles */
 
-#define TYPE_QEMU_CONSOLE "qemu-console"
-OBJECT_DECLARE_TYPE(QemuConsole, QemuConsoleClass, QEMU_CONSOLE)
-
-
 struct QemuConsoleClass {
     ObjectClass parent_class;
 };
diff --git a/ui/console.c b/ui/console.c
index 3d884956b7..ed9e7137b8 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -106,13 +106,8 @@ typedef struct QemuGraphicConsole {
 
 typedef QemuConsoleClass QemuGraphicConsoleClass;
 
-#define TYPE_QEMU_GRAPHIC_CONSOLE "qemu-graphic-console"
-OBJECT_DECLARE_SIMPLE_TYPE(QemuGraphicConsole, QEMU_GRAPHIC_CONSOLE)
 OBJECT_DEFINE_TYPE(QemuGraphicConsole, qemu_graphic_console, QEMU_GRAPHIC_CONSOLE, QEMU_CONSOLE)
 
-#define QEMU_IS_GRAPHIC_CONSOLE(c) \
-    object_dynamic_cast(OBJECT(c), TYPE_QEMU_GRAPHIC_CONSOLE)
-
 typedef struct QemuTextConsole {
     QemuConsole parent;
 
@@ -139,26 +134,16 @@ typedef struct QemuTextConsole {
 
 typedef QemuConsoleClass QemuTextConsoleClass;
 
-#define TYPE_QEMU_TEXT_CONSOLE "qemu-text-console"
-OBJECT_DECLARE_SIMPLE_TYPE(QemuTextConsole, QEMU_TEXT_CONSOLE)
 OBJECT_DEFINE_TYPE(QemuTextConsole, qemu_text_console, QEMU_TEXT_CONSOLE, QEMU_CONSOLE)
 
-#define QEMU_IS_TEXT_CONSOLE(c) \
-    object_dynamic_cast(OBJECT(c), TYPE_QEMU_TEXT_CONSOLE)
-
 typedef struct QemuFixedTextConsole {
     QemuTextConsole parent;
 } QemuFixedTextConsole;
 
 typedef QemuTextConsoleClass QemuFixedTextConsoleClass;
 
-#define TYPE_QEMU_FIXED_TEXT_CONSOLE "qemu-fixed-text-console"
-OBJECT_DECLARE_SIMPLE_TYPE(QemuFixedTextConsole, QEMU_FIXED_TEXT_CONSOLE)
 OBJECT_DEFINE_TYPE(QemuFixedTextConsole, qemu_fixed_text_console, QEMU_FIXED_TEXT_CONSOLE, QEMU_TEXT_CONSOLE)
 
-#define QEMU_IS_FIXED_TEXT_CONSOLE(c) \
-    object_dynamic_cast(OBJECT(c), TYPE_QEMU_FIXED_TEXT_CONSOLE)
-
 struct VCChardev {
     Chardev parent;
     QemuTextConsole *console;
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 36/52] ui/console: use QEMU_PIXMAN_COLOR helpers
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (34 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 35/52] ui/console: declare console types in console.h marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 37/52] ui/console: rename vga_ functions with qemu_console_ marcandre.lureau
                   ` (16 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

QEMU_RGB macro is actually defining a pixman color. Make this explicit
in the macro name. Move it to qemu-pixman.h so it can be used elsewhere,
as done in the following patch. Finally, define
QEMU_PIXMAN_COLOR_{BLACK,GRAY}, to avoid need to look up the VGA color
table from the QemuConsole placeholder surface rendering.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Message-Id: <20230830093843.3531473-37-marcandre.lureau@redhat.com>
---
 include/ui/qemu-pixman.h |  6 ++++++
 ui/console.c             | 39 ++++++++++++++++++---------------------
 2 files changed, 24 insertions(+), 21 deletions(-)

diff --git a/include/ui/qemu-pixman.h b/include/ui/qemu-pixman.h
index ce4518e4de..51f8709327 100644
--- a/include/ui/qemu-pixman.h
+++ b/include/ui/qemu-pixman.h
@@ -47,6 +47,12 @@
 # define PIXMAN_LE_x8r8g8b8   PIXMAN_x8r8g8b8
 #endif
 
+#define QEMU_PIXMAN_COLOR(r, g, b)                                               \
+    { .red = r << 8, .green = g << 8, .blue = b << 8, .alpha = 0xffff }
+
+#define QEMU_PIXMAN_COLOR_BLACK QEMU_PIXMAN_COLOR(0x00, 0x00, 0x00)
+#define QEMU_PIXMAN_COLOR_GRAY QEMU_PIXMAN_COLOR(0xaa, 0xaa, 0xaa)
+
 /* -------------------------------------------------------------------- */
 
 typedef struct PixelFormat {
diff --git a/ui/console.c b/ui/console.c
index ed9e7137b8..88e37eaff3 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -363,29 +363,26 @@ static void vga_bitblt(QemuConsole *con,
 
 #include "vgafont.h"
 
-#define QEMU_RGB(r, g, b)                                               \
-    { .red = r << 8, .green = g << 8, .blue = b << 8, .alpha = 0xffff }
-
 static const pixman_color_t color_table_rgb[2][8] = {
     {   /* dark */
-        [QEMU_COLOR_BLACK]   = QEMU_RGB(0x00, 0x00, 0x00),  /* black */
-        [QEMU_COLOR_BLUE]    = QEMU_RGB(0x00, 0x00, 0xaa),  /* blue */
-        [QEMU_COLOR_GREEN]   = QEMU_RGB(0x00, 0xaa, 0x00),  /* green */
-        [QEMU_COLOR_CYAN]    = QEMU_RGB(0x00, 0xaa, 0xaa),  /* cyan */
-        [QEMU_COLOR_RED]     = QEMU_RGB(0xaa, 0x00, 0x00),  /* red */
-        [QEMU_COLOR_MAGENTA] = QEMU_RGB(0xaa, 0x00, 0xaa),  /* magenta */
-        [QEMU_COLOR_YELLOW]  = QEMU_RGB(0xaa, 0xaa, 0x00),  /* yellow */
-        [QEMU_COLOR_WHITE]   = QEMU_RGB(0xaa, 0xaa, 0xaa),  /* white */
+        [QEMU_COLOR_BLACK]   = QEMU_PIXMAN_COLOR_BLACK,
+        [QEMU_COLOR_BLUE]    = QEMU_PIXMAN_COLOR(0x00, 0x00, 0xaa),  /* blue */
+        [QEMU_COLOR_GREEN]   = QEMU_PIXMAN_COLOR(0x00, 0xaa, 0x00),  /* green */
+        [QEMU_COLOR_CYAN]    = QEMU_PIXMAN_COLOR(0x00, 0xaa, 0xaa),  /* cyan */
+        [QEMU_COLOR_RED]     = QEMU_PIXMAN_COLOR(0xaa, 0x00, 0x00),  /* red */
+        [QEMU_COLOR_MAGENTA] = QEMU_PIXMAN_COLOR(0xaa, 0x00, 0xaa),  /* magenta */
+        [QEMU_COLOR_YELLOW]  = QEMU_PIXMAN_COLOR(0xaa, 0xaa, 0x00),  /* yellow */
+        [QEMU_COLOR_WHITE]   = QEMU_PIXMAN_COLOR_GRAY,
     },
     {   /* bright */
-        [QEMU_COLOR_BLACK]   = QEMU_RGB(0x00, 0x00, 0x00),  /* black */
-        [QEMU_COLOR_BLUE]    = QEMU_RGB(0x00, 0x00, 0xff),  /* blue */
-        [QEMU_COLOR_GREEN]   = QEMU_RGB(0x00, 0xff, 0x00),  /* green */
-        [QEMU_COLOR_CYAN]    = QEMU_RGB(0x00, 0xff, 0xff),  /* cyan */
-        [QEMU_COLOR_RED]     = QEMU_RGB(0xff, 0x00, 0x00),  /* red */
-        [QEMU_COLOR_MAGENTA] = QEMU_RGB(0xff, 0x00, 0xff),  /* magenta */
-        [QEMU_COLOR_YELLOW]  = QEMU_RGB(0xff, 0xff, 0x00),  /* yellow */
-        [QEMU_COLOR_WHITE]   = QEMU_RGB(0xff, 0xff, 0xff),  /* white */
+        [QEMU_COLOR_BLACK]   = QEMU_PIXMAN_COLOR_BLACK,
+        [QEMU_COLOR_BLUE]    = QEMU_PIXMAN_COLOR(0x00, 0x00, 0xff),  /* blue */
+        [QEMU_COLOR_GREEN]   = QEMU_PIXMAN_COLOR(0x00, 0xff, 0x00),  /* green */
+        [QEMU_COLOR_CYAN]    = QEMU_PIXMAN_COLOR(0x00, 0xff, 0xff),  /* cyan */
+        [QEMU_COLOR_RED]     = QEMU_PIXMAN_COLOR(0xff, 0x00, 0x00),  /* red */
+        [QEMU_COLOR_MAGENTA] = QEMU_PIXMAN_COLOR(0xff, 0x00, 0xff),  /* magenta */
+        [QEMU_COLOR_YELLOW]  = QEMU_PIXMAN_COLOR(0xff, 0xff, 0x00),  /* yellow */
+        [QEMU_COLOR_WHITE]   = QEMU_PIXMAN_COLOR(0xff, 0xff, 0xff),  /* white */
     }
 };
 
@@ -1520,8 +1517,8 @@ DisplaySurface *qemu_create_placeholder_surface(int w, int h,
                                                 const char *msg)
 {
     DisplaySurface *surface = qemu_create_displaysurface(w, h);
-    pixman_color_t bg = color_table_rgb[0][QEMU_COLOR_BLACK];
-    pixman_color_t fg = color_table_rgb[0][QEMU_COLOR_WHITE];
+    pixman_color_t bg = QEMU_PIXMAN_COLOR_BLACK;
+    pixman_color_t fg = QEMU_PIXMAN_COLOR_GRAY;
     pixman_image_t *glyph;
     int len, x, y, i;
 
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 37/52] ui/console: rename vga_ functions with qemu_console_
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (35 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 36/52] ui/console: use QEMU_PIXMAN_COLOR helpers marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 38/52] ui/console: assert(surface) where appropriate marcandre.lureau
                   ` (15 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

They are not specific to VGA. Let's use the object type name as prefix
instead, to avoid confusion.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Message-Id: <20230830093843.3531473-38-marcandre.lureau@redhat.com>
---
 ui/console.c | 25 ++++++++++++-------------
 1 file changed, 12 insertions(+), 13 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 88e37eaff3..a157a5b31c 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -331,9 +331,8 @@ void graphic_hw_text_update(QemuConsole *con, console_ch_t *chardata)
     }
 }
 
-static void vga_fill_rect(QemuConsole *con,
-                          int posx, int posy, int width, int height,
-                          pixman_color_t color)
+static void qemu_console_fill_rect(QemuConsole *con, int posx, int posy,
+                                   int width, int height, pixman_color_t color)
 {
     DisplaySurface *surface = qemu_console_surface(con);
     pixman_rectangle16_t rect = {
@@ -345,8 +344,8 @@ static void vga_fill_rect(QemuConsole *con,
 }
 
 /* copy from (xs, ys) to (xd, yd) a rectangle of size (w, h) */
-static void vga_bitblt(QemuConsole *con,
-                       int xs, int ys, int xd, int yd, int w, int h)
+static void qemu_console_bitblt(QemuConsole *con,
+                                int xs, int ys, int xd, int yd, int w, int h)
 {
     DisplaySurface *surface = qemu_console_surface(con);
 
@@ -526,8 +525,8 @@ static void console_refresh(QemuTextConsole *s)
     s->text_y[1] = s->height - 1;
     s->cursor_invalidate = 1;
 
-    vga_fill_rect(QEMU_CONSOLE(s), 0, 0, surface_width(surface), surface_height(surface),
-                  color_table_rgb[0][QEMU_COLOR_BLACK]);
+    qemu_console_fill_rect(QEMU_CONSOLE(s), 0, 0, surface_width(surface), surface_height(surface),
+                           color_table_rgb[0][QEMU_COLOR_BLACK]);
     y1 = s->y_displayed;
     for (y = 0; y < s->height; y++) {
         c = s->cells + y1 * s->width;
@@ -605,12 +604,12 @@ static void vc_put_lf(VCChardev *vc)
             s->text_x[1] = s->width - 1;
             s->text_y[1] = s->height - 1;
 
-            vga_bitblt(QEMU_CONSOLE(s), 0, FONT_HEIGHT, 0, 0,
-                       s->width * FONT_WIDTH,
-                       (s->height - 1) * FONT_HEIGHT);
-            vga_fill_rect(QEMU_CONSOLE(s), 0, (s->height - 1) * FONT_HEIGHT,
-                          s->width * FONT_WIDTH, FONT_HEIGHT,
-                          color_table_rgb[0][TEXT_ATTRIBUTES_DEFAULT.bgcol]);
+            qemu_console_bitblt(QEMU_CONSOLE(s), 0, FONT_HEIGHT, 0, 0,
+                                s->width * FONT_WIDTH,
+                                (s->height - 1) * FONT_HEIGHT);
+            qemu_console_fill_rect(QEMU_CONSOLE(s), 0, (s->height - 1) * FONT_HEIGHT,
+                                   s->width * FONT_WIDTH, FONT_HEIGHT,
+                                   color_table_rgb[0][TEXT_ATTRIBUTES_DEFAULT.bgcol]);
             s->update_x0 = 0;
             s->update_y0 = 0;
             s->update_x1 = s->width * FONT_WIDTH;
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 38/52] ui/console: assert(surface) where appropriate
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (36 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 37/52] ui/console: rename vga_ functions with qemu_console_ marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 39/52] ui/console: fold text_console_update_cursor_timer marcandre.lureau
                   ` (14 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

The QemuTextConsole code paths assume a surface is being used as
scanout, let's make this more explicit.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-39-marcandre.lureau@redhat.com>
---
 ui/console.c | 4 ++++
 1 file changed, 4 insertions(+)

diff --git a/ui/console.c b/ui/console.c
index a157a5b31c..04ec2d2488 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -339,6 +339,7 @@ static void qemu_console_fill_rect(QemuConsole *con, int posx, int posy,
         .x = posx, .y = posy, .width = width, .height = height
     };
 
+    assert(surface);
     pixman_image_fill_rectangles(PIXMAN_OP_SRC, surface->image,
                                  &color, 1, &rect);
 }
@@ -349,6 +350,7 @@ static void qemu_console_bitblt(QemuConsole *con,
 {
     DisplaySurface *surface = qemu_console_surface(con);
 
+    assert(surface);
     pixman_image_composite(PIXMAN_OP_SRC,
                            surface->image, NULL, surface->image,
                            xs, ys, 0, 0, xd, yd, w, h);
@@ -392,6 +394,7 @@ static void vga_putcharxy(QemuConsole *s, int x, int y, int ch,
     DisplaySurface *surface = qemu_console_surface(s);
     pixman_color_t fgcol, bgcol;
 
+    assert(surface);
     if (t_attrib->invers) {
         bgcol = color_table_rgb[t_attrib->bold][t_attrib->fgcol];
         fgcol = color_table_rgb[t_attrib->bold][t_attrib->bgcol];
@@ -519,6 +522,7 @@ static void console_refresh(QemuTextConsole *s)
     TextCell *c;
     int x, y, y1;
 
+    assert(surface);
     s->text_x[0] = 0;
     s->text_y[0] = 0;
     s->text_x[1] = s->width - 1;
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 39/52] ui/console: fold text_console_update_cursor_timer
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (37 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 38/52] ui/console: assert(surface) where appropriate marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 40/52] ui/vc: skip text console resize when possible marcandre.lureau
                   ` (13 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Message-Id: <20230830093843.3531473-40-marcandre.lureau@redhat.com>
---
 ui/console.c | 10 ++--------
 1 file changed, 2 insertions(+), 8 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 04ec2d2488..0a48ce9159 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -174,7 +174,6 @@ static QEMUTimer *cursor_timer;
 
 static void dpy_refresh(DisplayState *s);
 static DisplayState *get_alloc_displaystate(void);
-static void text_console_update_cursor_timer(void);
 static void text_console_update_cursor(void *opaque);
 static bool displaychangelistener_has_dmabuf(DisplayChangeListener *dcl);
 static bool console_compatible_with(QemuConsole *con,
@@ -2497,12 +2496,6 @@ static void vc_chr_set_echo(Chardev *chr, bool echo)
     drv->console->echo = echo;
 }
 
-static void text_console_update_cursor_timer(void)
-{
-    timer_mod(cursor_timer, qemu_clock_get_ms(QEMU_CLOCK_REALTIME)
-              + CONSOLE_CURSOR_PERIOD / 2);
-}
-
 static void text_console_update_cursor(void *opaque)
 {
     QemuConsole *s;
@@ -2520,7 +2513,8 @@ static void text_console_update_cursor(void *opaque)
     }
 
     if (count) {
-        text_console_update_cursor_timer();
+        timer_mod(cursor_timer,
+                  qemu_clock_get_ms(QEMU_CLOCK_REALTIME) + CONSOLE_CURSOR_PERIOD / 2);
     }
 }
 
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 40/52] ui/vc: skip text console resize when possible
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (38 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 39/52] ui/console: fold text_console_update_cursor_timer marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 41/52] ui/console: minor stylistic changes marcandre.lureau
                   ` (12 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

This function is called on invalidate, on each cursor blink.

Avoid the extra copy when the console size didn't change.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-41-marcandre.lureau@redhat.com>
---
 ui/console.c | 12 +++++++++---
 1 file changed, 9 insertions(+), 3 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 0a48ce9159..4ee3b77568 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -413,13 +413,19 @@ static void text_console_resize(QemuTextConsole *t)
 {
     QemuConsole *s = QEMU_CONSOLE(t);
     TextCell *cells, *c, *c1;
-    int w1, x, y, last_width;
+    int w1, x, y, last_width, w, h;
 
     assert(s->scanout.kind == SCANOUT_SURFACE);
 
+    w = surface_width(s->surface) / FONT_WIDTH;
+    h = surface_height(s->surface) / FONT_HEIGHT;
+    if (w == t->width && h == t->height) {
+        return;
+    }
+
     last_width = t->width;
-    t->width = surface_width(s->surface) / FONT_WIDTH;
-    t->height = surface_height(s->surface) / FONT_HEIGHT;
+    t->width = w;
+    t->height = h;
 
     w1 = last_width;
     if (t->width < w1)
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 41/52] ui/console: minor stylistic changes
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (39 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 40/52] ui/vc: skip text console resize when possible marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 42/52] ui/vc: move text console invalidate in helper marcandre.lureau
                   ` (11 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-42-marcandre.lureau@redhat.com>
---
 ui/console.c | 10 ++++------
 1 file changed, 4 insertions(+), 6 deletions(-)

diff --git a/ui/console.c b/ui/console.c
index 4ee3b77568..b1d375ecb4 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -427,20 +427,18 @@ static void text_console_resize(QemuTextConsole *t)
     t->width = w;
     t->height = h;
 
-    w1 = last_width;
-    if (t->width < w1)
-        w1 = t->width;
+    w1 = MIN(t->width, last_width);
 
     cells = g_new(TextCell, t->width * t->total_height + 1);
-    for(y = 0; y < t->total_height; y++) {
+    for (y = 0; y < t->total_height; y++) {
         c = &cells[y * t->width];
         if (w1 > 0) {
             c1 = &t->cells[y * last_width];
-            for(x = 0; x < w1; x++) {
+            for (x = 0; x < w1; x++) {
                 *c++ = *c1++;
             }
         }
-        for(x = w1; x < t->width; x++) {
+        for (x = w1; x < t->width; x++) {
             c->ch = ' ';
             c->t_attrib = TEXT_ATTRIBUTES_DEFAULT;
             c++;
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 42/52] ui/vc: move text console invalidate in helper
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (40 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 41/52] ui/console: minor stylistic changes marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 43/52] ui/vc: do not parse VC-specific options in Spice and GTK marcandre.lureau
                   ` (10 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

This will allow to split the VC code in a separate unit more easily.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-43-marcandre.lureau@redhat.com>
---
 include/ui/console.h |  1 +
 ui/console.c         | 13 +++++++++----
 2 files changed, 10 insertions(+), 4 deletions(-)

diff --git a/include/ui/console.h b/include/ui/console.h
index 0f7f50deaf..91d8bbc9dc 100644
--- a/include/ui/console.h
+++ b/include/ui/console.h
@@ -521,6 +521,7 @@ void console_select(unsigned int index);
 void qemu_console_resize(QemuConsole *con, int width, int height);
 DisplaySurface *qemu_console_surface(QemuConsole *con);
 void coroutine_fn qemu_console_co_wait_update(QemuConsole *con);
+int qemu_invalidate_text_consoles(void);
 
 /* console-gl.c */
 #ifdef CONFIG_OPENGL
diff --git a/ui/console.c b/ui/console.c
index b1d375ecb4..ba9da8c1b3 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -2500,13 +2500,11 @@ static void vc_chr_set_echo(Chardev *chr, bool echo)
     drv->console->echo = echo;
 }
 
-static void text_console_update_cursor(void *opaque)
+int qemu_invalidate_text_consoles(void)
 {
     QemuConsole *s;
     int count = 0;
 
-    cursor_visible_phase = !cursor_visible_phase;
-
     QTAILQ_FOREACH(s, &consoles, next) {
         if (qemu_console_is_graphic(s) ||
             !qemu_console_is_visible(s)) {
@@ -2516,7 +2514,14 @@ static void text_console_update_cursor(void *opaque)
         graphic_hw_invalidate(s);
     }
 
-    if (count) {
+    return count;
+}
+
+static void text_console_update_cursor(void *opaque)
+{
+    cursor_visible_phase = !cursor_visible_phase;
+
+    if (qemu_invalidate_text_consoles()) {
         timer_mod(cursor_timer,
                   qemu_clock_get_ms(QEMU_CLOCK_REALTIME) + CONSOLE_CURSOR_PERIOD / 2);
     }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 43/52] ui/vc: do not parse VC-specific options in Spice and GTK
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (41 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 42/52] ui/vc: move text console invalidate in helper marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 44/52] ui/vc: change the argument for QemuTextConsole marcandre.lureau
                   ` (9 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel
  Cc: stefanha, Marc-André Lureau, Paolo Bonzini, Eric Blake,
	Markus Armbruster, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

In commit 6f974c843c ("gtk: overwrite the console.c char driver"), I
shared the VC console parse handler with GTK. And later on in commit
d8aec9d9 ("display: add -display spice-app launching a Spice client"),
I also used it to handle spice-app VC.

This is not necessary, the VC console options (width/height/cols/rows)
are specific, and unused by tty-level GTK/Spice VC.

This is not a breaking change, as those options are still being parsed
by QAPI ChardevVC. Adjust the documentation about it.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-44-marcandre.lureau@redhat.com>
---
 qapi/char.json         | 4 ++++
 include/chardev/char.h | 3 ---
 ui/console.c           | 4 ++--
 ui/gtk.c               | 1 -
 ui/spice-app.c         | 7 ++++++-
 5 files changed, 12 insertions(+), 7 deletions(-)

diff --git a/qapi/char.json b/qapi/char.json
index 52aaff25eb..c1bab7b855 100644
--- a/qapi/char.json
+++ b/qapi/char.json
@@ -390,6 +390,10 @@
 #
 # @rows: console height, in chars
 #
+# Note: the options are only effective when the VNC or SDL graphical
+# display backend is active. They are ignored with the GTK, Spice, VNC
+# and D-Bus display backends.
+#
 # Since: 1.5
 ##
 { 'struct': 'ChardevVC',
diff --git a/include/chardev/char.h b/include/chardev/char.h
index 44cd82e405..01df55f9e8 100644
--- a/include/chardev/char.h
+++ b/include/chardev/char.h
@@ -320,7 +320,4 @@ GSource *qemu_chr_timeout_add_ms(Chardev *chr, guint ms,
 void suspend_mux_open(void);
 void resume_mux_open(void);
 
-/* console.c */
-void qemu_chr_parse_vc(QemuOpts *opts, ChardevBackend *backend, Error **errp);
-
 #endif
diff --git a/ui/console.c b/ui/console.c
index ba9da8c1b3..e2b0b9ce06 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -2708,7 +2708,7 @@ void qemu_display_help(void)
     }
 }
 
-void qemu_chr_parse_vc(QemuOpts *opts, ChardevBackend *backend, Error **errp)
+static void vc_chr_parse(QemuOpts *opts, ChardevBackend *backend, Error **errp)
 {
     int val;
     ChardevVC *vc;
@@ -2746,7 +2746,7 @@ static void char_vc_class_init(ObjectClass *oc, void *data)
 {
     ChardevClass *cc = CHARDEV_CLASS(oc);
 
-    cc->parse = qemu_chr_parse_vc;
+    cc->parse = vc_chr_parse;
     cc->open = vc_chr_open;
     cc->chr_write = vc_chr_write;
     cc->chr_accept_input = vc_chr_accept_input;
diff --git a/ui/gtk.c b/ui/gtk.c
index 8ba41c8f13..ef98bb0648 100644
--- a/ui/gtk.c
+++ b/ui/gtk.c
@@ -1860,7 +1860,6 @@ static void char_gd_vc_class_init(ObjectClass *oc, void *data)
 {
     ChardevClass *cc = CHARDEV_CLASS(oc);
 
-    cc->parse = qemu_chr_parse_vc;
     cc->open = gd_vc_open;
     cc->chr_write = gd_vc_chr_write;
     cc->chr_accept_input = gd_vc_chr_accept_input;
diff --git a/ui/spice-app.c b/ui/spice-app.c
index ad7f0551ad..405fb7f9f5 100644
--- a/ui/spice-app.c
+++ b/ui/spice-app.c
@@ -96,6 +96,11 @@ static void vc_chr_set_echo(Chardev *chr, bool echo)
     /* TODO: set echo for frontends QMP and qtest */
 }
 
+static void vc_chr_parse(QemuOpts *opts, ChardevBackend *backend, Error **errp)
+{
+    /* fqdn is dealt with in vc_chr_open() */
+}
+
 static void char_vc_class_init(ObjectClass *oc, void *data)
 {
     VCChardevClass *vc = CHARDEV_VC_CLASS(oc);
@@ -103,7 +108,7 @@ static void char_vc_class_init(ObjectClass *oc, void *data)
 
     vc->parent_open = cc->open;
 
-    cc->parse = qemu_chr_parse_vc;
+    cc->parse = vc_chr_parse;
     cc->open = vc_chr_open;
     cc->chr_set_echo = vc_chr_set_echo;
 }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 44/52] ui/vc: change the argument for QemuTextConsole
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (42 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 43/52] ui/vc: do not parse VC-specific options in Spice and GTK marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 45/52] ui/spice-display: Avoid dynamic stack allocation marcandre.lureau
                   ` (8 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Marc-André Lureau, Gerd Hoffmann

From: Marc-André Lureau <marcandre.lureau@redhat.com>

Those functions are specifc to text/vc console, make that explicit from
the argument type.

Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Reviewed-by: Daniel P. Berrangé <berrange@redhat.com>
Message-Id: <20230830093843.3531473-45-marcandre.lureau@redhat.com>
---
 include/ui/console.h |  6 +++---
 ui/console.c         | 14 ++++++--------
 ui/gtk.c             |  2 +-
 ui/sdl2-input.c      |  7 ++++---
 ui/sdl2.c            |  5 ++---
 5 files changed, 16 insertions(+), 18 deletions(-)

diff --git a/include/ui/console.h b/include/ui/console.h
index 91d8bbc9dc..1ccd432b4d 100644
--- a/include/ui/console.h
+++ b/include/ui/console.h
@@ -112,9 +112,9 @@ bool qemu_mouse_set(int index, Error **errp);
 #define QEMU_KEY_CTRL_PAGEUP     0xe406
 #define QEMU_KEY_CTRL_PAGEDOWN   0xe407
 
-void kbd_put_keysym_console(QemuConsole *s, int keysym);
-bool kbd_put_qcode_console(QemuConsole *s, int qcode, bool ctrl);
-void kbd_put_string_console(QemuConsole *s, const char *str, int len);
+void kbd_put_keysym_console(QemuTextConsole *s, int keysym);
+bool kbd_put_qcode_console(QemuTextConsole *s, int qcode, bool ctrl);
+void kbd_put_string_console(QemuTextConsole *s, const char *str, int len);
 void kbd_put_keysym(int keysym);
 
 /* Touch devices */
diff --git a/ui/console.c b/ui/console.c
index e2b0b9ce06..e4d61794bb 100644
--- a/ui/console.c
+++ b/ui/console.c
@@ -1135,16 +1135,12 @@ static void kbd_send_chars(QemuTextConsole *s)
 }
 
 /* called when an ascii key is pressed */
-void kbd_put_keysym_console(QemuConsole *con, int keysym)
+void kbd_put_keysym_console(QemuTextConsole *s, int keysym)
 {
-    QemuTextConsole *s = (QemuTextConsole *)object_dynamic_cast(OBJECT(con), TYPE_QEMU_TEXT_CONSOLE);
     uint8_t buf[16], *q;
     int c;
     uint32_t num_free;
 
-    if (!s)
-        return;
-
     switch(keysym) {
     case QEMU_KEY_CTRL_UP:
         console_scroll(s, -1);
@@ -1214,7 +1210,7 @@ static const int ctrl_qcode_to_keysym[Q_KEY_CODE__MAX] = {
     [Q_KEY_CODE_PGDN]   = QEMU_KEY_CTRL_PAGEDOWN,
 };
 
-bool kbd_put_qcode_console(QemuConsole *s, int qcode, bool ctrl)
+bool kbd_put_qcode_console(QemuTextConsole *s, int qcode, bool ctrl)
 {
     int keysym;
 
@@ -1226,7 +1222,7 @@ bool kbd_put_qcode_console(QemuConsole *s, int qcode, bool ctrl)
     return true;
 }
 
-void kbd_put_string_console(QemuConsole *s, const char *str, int len)
+void kbd_put_string_console(QemuTextConsole *s, const char *str, int len)
 {
     int i;
 
@@ -1237,7 +1233,9 @@ void kbd_put_string_console(QemuConsole *s, const char *str, int len)
 
 void kbd_put_keysym(int keysym)
 {
-    kbd_put_keysym_console(active_console, keysym);
+    if (QEMU_IS_TEXT_CONSOLE(active_console)) {
+        kbd_put_keysym_console(QEMU_TEXT_CONSOLE(active_console), keysym);
+    }
 }
 
 static void text_console_invalidate(void *opaque)
diff --git a/ui/gtk.c b/ui/gtk.c
index ef98bb0648..c34c133550 100644
--- a/ui/gtk.c
+++ b/ui/gtk.c
@@ -1187,7 +1187,7 @@ static gboolean gd_text_key_down(GtkWidget *widget,
                                  GdkEventKey *key, void *opaque)
 {
     VirtualConsole *vc = opaque;
-    QemuConsole *con = vc->gfx.dcl.con;
+    QemuTextConsole *con = QEMU_TEXT_CONSOLE(vc->gfx.dcl.con);
 
     if (key->keyval == GDK_KEY_Delete) {
         kbd_put_qcode_console(con, Q_KEY_CODE_DELETE, false);
diff --git a/ui/sdl2-input.c b/ui/sdl2-input.c
index f068382209..a318cc5867 100644
--- a/ui/sdl2-input.c
+++ b/ui/sdl2-input.c
@@ -43,15 +43,16 @@ void sdl2_process_key(struct sdl2_console *scon,
                            ev->type == SDL_KEYDOWN ? "down" : "up");
     qkbd_state_key_event(scon->kbd, qcode, ev->type == SDL_KEYDOWN);
 
-    if (!qemu_console_is_graphic(con)) {
+    if (QEMU_IS_TEXT_CONSOLE(con)) {
+        QemuTextConsole *s = QEMU_TEXT_CONSOLE(con);
         bool ctrl = qkbd_state_modifier_get(scon->kbd, QKBD_MOD_CTRL);
         if (ev->type == SDL_KEYDOWN) {
             switch (qcode) {
             case Q_KEY_CODE_RET:
-                kbd_put_keysym_console(con, '\n');
+                kbd_put_keysym_console(s, '\n');
                 break;
             default:
-                kbd_put_qcode_console(con, qcode, ctrl);
+                kbd_put_qcode_console(s, qcode, ctrl);
                 break;
             }
         }
diff --git a/ui/sdl2.c b/ui/sdl2.c
index 0d91b555e3..16b515fcf9 100644
--- a/ui/sdl2.c
+++ b/ui/sdl2.c
@@ -483,10 +483,9 @@ static void handle_textinput(SDL_Event *ev)
         return;
     }
 
-    if (qemu_console_is_graphic(con)) {
-        return;
+    if (QEMU_IS_TEXT_CONSOLE(con)) {
+        kbd_put_string_console(QEMU_TEXT_CONSOLE(con), ev->text.text, strlen(ev->text.text));
     }
-    kbd_put_string_console(con, ev->text.text, strlen(ev->text.text));
 }
 
 static void handle_mousemotion(SDL_Event *ev)
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 45/52] ui/spice-display: Avoid dynamic stack allocation
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (43 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 44/52] ui/vc: change the argument for QemuTextConsole marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 46/52] ui/vnc-enc-hextile: Use static rather than dynamic length stack array marcandre.lureau
                   ` (7 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Peter Maydell, Gerd Hoffmann, Marc-André Lureau

From: Peter Maydell <peter.maydell@linaro.org>

Use an autofree heap allocation instead of a variable-length
array on the stack in qemu_spice_create_update().

The codebase has very few VLAs, and if we can get rid of them all we
can make the compiler error on new additions.  This is a defensive
measure against security bugs where an on-stack dynamic allocation
isn't correctly size-checked (e.g.  CVE-2021-3527).

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Message-Id: <20230818151057.1541189-2-peter.maydell@linaro.org>
---
 ui/spice-display.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/ui/spice-display.c b/ui/spice-display.c
index 3f3f8013d8..0e2fbfb17c 100644
--- a/ui/spice-display.c
+++ b/ui/spice-display.c
@@ -189,7 +189,7 @@ static void qemu_spice_create_update(SimpleSpiceDisplay *ssd)
 {
     static const int blksize = 32;
     int blocks = DIV_ROUND_UP(surface_width(ssd->ds), blksize);
-    int dirty_top[blocks];
+    g_autofree int *dirty_top = NULL;
     int y, yoff1, yoff2, x, xoff, blk, bw;
     int bpp = surface_bytes_per_pixel(ssd->ds);
     uint8_t *guest, *mirror;
@@ -198,6 +198,7 @@ static void qemu_spice_create_update(SimpleSpiceDisplay *ssd)
         return;
     };
 
+    dirty_top = g_new(int, blocks);
     for (blk = 0; blk < blocks; blk++) {
         dirty_top[blk] = -1;
     }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 46/52] ui/vnc-enc-hextile: Use static rather than dynamic length stack array
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (44 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 45/52] ui/spice-display: Avoid dynamic stack allocation marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 47/52] ui/vnc-enc-tight: Avoid dynamic stack allocation marcandre.lureau
                   ` (6 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Peter Maydell, Marc-André Lureau, Gerd Hoffmann

From: Peter Maydell <peter.maydell@linaro.org>

In the send_hextile_tile_* function we create a variable length array
data[].  In fact we know that the client_pf.bytes_per_pixel is at
most 4 (enforced by set_pixel_format()), so we can make the array a
compile-time fixed length of 1536 bytes.

The codebase has very few VLAs, and if we can get rid of them all we
can make the compiler error on new additions.  This is a defensive
measure against security bugs where an on-stack dynamic allocation
isn't correctly size-checked (e.g.  CVE-2021-3527).

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Philippe Mathieu-Daudé <philmd@linaro.org>
[ Marc-André - rename BPP to MAX_BYTES_PER_PIXEL ]
Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Message-Id: <20230818151057.1541189-3-peter.maydell@linaro.org>
---
 ui/vnc-enc-hextile-template.h | 8 +++++++-
 1 file changed, 7 insertions(+), 1 deletion(-)

diff --git a/ui/vnc-enc-hextile-template.h b/ui/vnc-enc-hextile-template.h
index 0c56262aff..8ee92086ac 100644
--- a/ui/vnc-enc-hextile-template.h
+++ b/ui/vnc-enc-hextile-template.h
@@ -7,6 +7,8 @@
 #define NAME BPP
 #endif
 
+#define MAX_BYTES_PER_PIXEL 4
+
 static void CONCAT(send_hextile_tile_, NAME)(VncState *vs,
                                              int x, int y, int w, int h,
                                              void *last_bg_,
@@ -25,10 +27,13 @@ static void CONCAT(send_hextile_tile_, NAME)(VncState *vs,
     int bg_count = 0;
     int fg_count = 0;
     int flags = 0;
-    uint8_t data[(vs->client_pf.bytes_per_pixel + 2) * 16 * 16];
+    uint8_t data[(MAX_BYTES_PER_PIXEL + 2) * 16 * 16];
     int n_data = 0;
     int n_subtiles = 0;
 
+    /* Enforced by set_pixel_format() */
+    assert(vs->client_pf.bytes_per_pixel <= MAX_BYTES_PER_PIXEL);
+
     for (j = 0; j < h; j++) {
         for (i = 0; i < w; i++) {
             switch (n_colors) {
@@ -205,6 +210,7 @@ static void CONCAT(send_hextile_tile_, NAME)(VncState *vs,
     }
 }
 
+#undef MAX_BYTES_PER_PIXEL
 #undef NAME
 #undef pixel_t
 #undef CONCAT_I
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 47/52] ui/vnc-enc-tight: Avoid dynamic stack allocation
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (45 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 46/52] ui/vnc-enc-hextile: Use static rather than dynamic length stack array marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 48/52] ui/dbus: Properly dispose touch/mouse dbus objects marcandre.lureau
                   ` (5 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel
  Cc: stefanha, Philippe Mathieu-Daudé, Peter Maydell,
	Gerd Hoffmann, Marc-André Lureau

From: Philippe Mathieu-Daudé <philmd@redhat.com>

Use autofree heap allocation instead of variable-length
array on the stack.

The codebase has very few VLAs, and if we can get rid of them all we
can make the compiler error on new additions.  This is a defensive
measure against security bugs where an on-stack dynamic allocation
isn't correctly size-checked (e.g.  CVE-2021-3527).

Signed-off-by: Philippe Mathieu-Daudé <philmd@redhat.com>
[PMM: expanded commit message]
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Francisco Iglesias <frasse.iglesias@gmail.com>
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Message-Id: <20230818151057.1541189-4-peter.maydell@linaro.org>
---
 ui/vnc-enc-tight.c | 11 ++++++-----
 1 file changed, 6 insertions(+), 5 deletions(-)

diff --git a/ui/vnc-enc-tight.c b/ui/vnc-enc-tight.c
index ee853dcfcb..41f559eb83 100644
--- a/ui/vnc-enc-tight.c
+++ b/ui/vnc-enc-tight.c
@@ -1097,13 +1097,13 @@ static int send_palette_rect(VncState *vs, int x, int y,
     switch (vs->client_pf.bytes_per_pixel) {
     case 4:
     {
-        size_t old_offset, offset;
-        uint32_t header[palette_size(palette)];
+        size_t old_offset, offset, palette_sz = palette_size(palette);
+        g_autofree uint32_t *header = g_new(uint32_t, palette_sz);
         struct palette_cb_priv priv = { vs, (uint8_t *)header };
 
         old_offset = vs->output.offset;
         palette_iter(palette, write_palette, &priv);
-        vnc_write(vs, header, sizeof(header));
+        vnc_write(vs, header, palette_sz * sizeof(uint32_t));
 
         if (vs->tight->pixel24) {
             tight_pack24(vs, vs->output.buffer + old_offset, colors, &offset);
@@ -1115,11 +1115,12 @@ static int send_palette_rect(VncState *vs, int x, int y,
     }
     case 2:
     {
-        uint16_t header[palette_size(palette)];
+        size_t palette_sz = palette_size(palette);
+        g_autofree uint16_t *header = g_new(uint16_t, palette_sz);
         struct palette_cb_priv priv = { vs, (uint8_t *)header };
 
         palette_iter(palette, write_palette, &priv);
-        vnc_write(vs, header, sizeof(header));
+        vnc_write(vs, header, palette_sz * sizeof(uint16_t));
         tight_encode_indexed_rect16(vs->tight->tight.buffer, w * h, palette);
         break;
     }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 48/52] ui/dbus: Properly dispose touch/mouse dbus objects
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (46 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 47/52] ui/vnc-enc-tight: Avoid dynamic stack allocation marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 49/52] ui/dbus: implement damage regions for GL marcandre.lureau
                   ` (4 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel
  Cc: stefanha, Bilal Elmoussaoui, Marc-André Lureau,
	Gerd Hoffmann

From: Bilal Elmoussaoui <belmouss@redhat.com>

Fixes: 142ca628a7 ("ui: add a D-Bus display backend")
Fixes: de9f844ce2 ("ui/dbus: Expose a touch device interface")

Signed-off-by: Bilal Elmoussaoui <belmouss@redhat.com>
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Message-Id: <20230901124507.94087-1-belmouss@redhat.com>
---
 ui/dbus-console.c | 2 ++
 1 file changed, 2 insertions(+)

diff --git a/ui/dbus-console.c b/ui/dbus-console.c
index e19774f985..36f7349585 100644
--- a/ui/dbus-console.c
+++ b/ui/dbus-console.c
@@ -150,6 +150,8 @@ dbus_display_console_dispose(GObject *object)
     DBusDisplayConsole *ddc = DBUS_DISPLAY_CONSOLE(object);
 
     unregister_displaychangelistener(&ddc->dcl);
+    g_clear_object(&ddc->iface_touch);
+    g_clear_object(&ddc->iface_mouse);
     g_clear_object(&ddc->iface_kbd);
     g_clear_object(&ddc->iface);
     g_clear_pointer(&ddc->listeners, g_hash_table_unref);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 49/52] ui/dbus: implement damage regions for GL
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (47 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 48/52] ui/dbus: Properly dispose touch/mouse dbus objects marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 50/52] ui/vdagent: call vdagent_disconnect() when agent connection is lost marcandre.lureau
                   ` (3 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel
  Cc: stefanha, Bilal Elmoussaoui, Marc-André Lureau,
	Gerd Hoffmann

From: Bilal Elmoussaoui <belmouss@redhat.com>

Currently, when using `-display dbus,gl=on` all updates to the client
become "full scanout" updates, meaning there is no way for the client to
limit damage regions to the display server.

Instead of using an "update count", this patch tracks the damage region
and propagates it to the client.

This was less of an issue when clients were using GtkGLArea for
rendering,
as you'd be doing full-surface redraw. To be efficient, the client needs
both a DMA-BUF and the damage region to be updated.

Co-authored-by: Christian Hergert <chergert@redhat.com>
Signed-off-by: Bilal Elmoussaoui <belmouss@redhat.com>
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Message-Id: <20230814125802.102160-1-belmouss@redhat.com>
---
 ui/dbus-listener.c | 32 +++++++++++++++++++++++++-------
 1 file changed, 25 insertions(+), 7 deletions(-)

diff --git a/ui/dbus-listener.c b/ui/dbus-listener.c
index 30917271ab..36548a7f52 100644
--- a/ui/dbus-listener.c
+++ b/ui/dbus-listener.c
@@ -26,6 +26,9 @@
 #include "qapi/error.h"
 #include "sysemu/sysemu.h"
 #include "dbus.h"
+#ifdef CONFIG_OPENGL
+#include <pixman.h>
+#endif
 #ifdef G_OS_UNIX
 #include <gio/gunixfdlist.h>
 #endif
@@ -59,12 +62,15 @@ struct _DBusDisplayListener {
 
     QemuDBusDisplay1Listener *proxy;
 
+#ifdef CONFIG_OPENGL
+    /* Keep track of the damage region */
+    pixman_region32_t gl_damage;
+#endif
+
     DisplayChangeListener dcl;
     DisplaySurface *ds;
     enum share_kind ds_share;
 
-    int gl_updates;
-
     bool ds_mapped;
     bool can_share_map;
 
@@ -539,11 +545,16 @@ static void dbus_gl_refresh(DisplayChangeListener *dcl)
         return;
     }
 
-    if (ddl->gl_updates) {
-        dbus_call_update_gl(dcl, 0, 0,
-                            surface_width(ddl->ds), surface_height(ddl->ds));
-        ddl->gl_updates = 0;
+    int n_rects = pixman_region32_n_rects(&ddl->gl_damage);
+
+    for (int i = 0; i < n_rects; i++) {
+        pixman_box32_t *box;
+        box = pixman_region32_rectangles(&ddl->gl_damage, NULL) + i;
+        /* TODO: Add a UpdateList call to send multiple updates at once */
+        dbus_call_update_gl(dcl, box->x1, box->y1,
+                            box->x2 - box->x1, box->y2 - box->y1);
     }
+    pixman_region32_clear(&ddl->gl_damage);
 }
 #endif /* OPENGL */
 
@@ -558,7 +569,10 @@ static void dbus_gl_gfx_update(DisplayChangeListener *dcl,
 {
     DBusDisplayListener *ddl = container_of(dcl, DBusDisplayListener, dcl);
 
-    ddl->gl_updates++;
+    pixman_region32_t rect_region;
+    pixman_region32_init_rect(&rect_region, x, y, w, h);
+    pixman_region32_union(&ddl->gl_damage, &ddl->gl_damage, &rect_region);
+    pixman_region32_fini(&rect_region);
 }
 #endif
 
@@ -738,6 +752,7 @@ dbus_display_listener_dispose(GObject *object)
     g_clear_object(&ddl->d3d11_proxy);
     g_clear_pointer(&ddl->peer_process, CloseHandle);
 #ifdef CONFIG_OPENGL
+    pixman_region32_fini(&ddl->gl_damage);
     egl_fb_destroy(&ddl->fb);
 #endif
 #endif
@@ -772,6 +787,9 @@ dbus_display_listener_class_init(DBusDisplayListenerClass *klass)
 static void
 dbus_display_listener_init(DBusDisplayListener *ddl)
 {
+#ifdef CONFIG_OPENGL
+    pixman_region32_init(&ddl->gl_damage);
+#endif
 }
 
 const char *
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 50/52] ui/vdagent: call vdagent_disconnect() when agent connection is lost
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (48 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 49/52] ui/dbus: implement damage regions for GL marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 51/52] ui/vdagent: Unregister input handler of mouse during finalization marcandre.lureau
                   ` (2 subsequent siblings)
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel
  Cc: stefanha, Guoyi Tu, dengpengcheng, Gerd Hoffmann,
	Marc-André Lureau

From: Guoyi Tu <tugy@chinatelecom.cn>

when the agent connection is lost, the input handler of the mouse
doesn't deactivate, which results in unresponsive mouse events in
VNC windows.

To fix this issue, call vdagent_disconnect() to reset the state
each time the frontend disconncect

Signed-off-by: Guoyi Tu <tugy@chinatelecom.cn>
Signed-off-by: dengpengcheng <dengpc12@chinatelecom.cn>
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Message-Id: <71fd5a58fd09f10cdb35f167b2edb5669300116e.1692281173.git.tugy@chinatelecom.cn>
---
 ui/vdagent.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/ui/vdagent.c b/ui/vdagent.c
index 8a651492f0..4b9a1fb7c5 100644
--- a/ui/vdagent.c
+++ b/ui/vdagent.c
@@ -870,8 +870,11 @@ static void vdagent_disconnect(VDAgentChardev *vd)
 
 static void vdagent_chr_set_fe_open(struct Chardev *chr, int fe_open)
 {
+    VDAgentChardev *vd = QEMU_VDAGENT_CHARDEV(chr);
+
     if (!fe_open) {
         trace_vdagent_close();
+        vdagent_disconnect(vd);
         /* To reset_serial, we CLOSED our side. Make sure the other end knows we
          * are ready again. */
         qemu_chr_be_event(chr, CHR_EVENT_OPENED);
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 51/52] ui/vdagent: Unregister input handler of mouse during finalization
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (49 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 50/52] ui/vdagent: call vdagent_disconnect() when agent connection is lost marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-04 11:52 ` [PULL 52/52] ui/gtk: fix leaks found wtih fuzzing marcandre.lureau
  2023-09-06 18:24 ` [PULL 00/52] UI patches Stefan Hajnoczi
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel
  Cc: stefanha, Guoyi Tu, dengpengcheng, Gerd Hoffmann,
	Marc-André Lureau

From: Guoyi Tu <tugy@chinatelecom.cn>

Input handler resource should be released when
VDAgentChardev object finalize

Signed-off-by: Guoyi Tu <tugy@chinatelecom.cn>
Signed-off-by: dengpengcheng <dengpc12@chinatelecom.cn>
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
Message-Id: <e7f5e172abf797d454e00a4bbe53af83e4aa4497.1692281173.git.tugy@chinatelecom.cn>
---
 ui/vdagent.c | 3 +++
 1 file changed, 3 insertions(+)

diff --git a/ui/vdagent.c b/ui/vdagent.c
index 4b9a1fb7c5..00d36a8677 100644
--- a/ui/vdagent.c
+++ b/ui/vdagent.c
@@ -926,6 +926,9 @@ static void vdagent_chr_fini(Object *obj)
 
     migrate_del_blocker(vd->migration_blocker);
     vdagent_disconnect(vd);
+    if (vd->mouse_hs) {
+        qemu_input_handler_unregister(vd->mouse_hs);
+    }
     buffer_free(&vd->outbuf);
     error_free(vd->migration_blocker);
 }
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* [PULL 52/52] ui/gtk: fix leaks found wtih fuzzing
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (50 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 51/52] ui/vdagent: Unregister input handler of mouse during finalization marcandre.lureau
@ 2023-09-04 11:52 ` marcandre.lureau
  2023-09-06 18:24 ` [PULL 00/52] UI patches Stefan Hajnoczi
  52 siblings, 0 replies; 54+ messages in thread
From: marcandre.lureau @ 2023-09-04 11:52 UTC (permalink / raw)
  To: qemu-devel; +Cc: stefanha, Dmitry Frolov, Gerd Hoffmann, Marc-André Lureau

From: Dmitry Frolov <frolov@swemel.ru>

It is true, that there is no problem during runtime
from the first sight, because the memory is lost just
before qemu exits. Nevertheless, this change is necessary,
because AddressSanitizer is not able to recognize this
situation and produces crash-report (which is
false-positive in fact). Lots of False-Positive warnings
are davaluing problems, found with fuzzing, and thus the
whole methodology of dynamic analysis.
This patch eliminates such False-Positive reports,
and makes every problem, found with fuzzing, more valuable.

Fixes: 060ab76356 ("gtk: don't exit early in case gtk init fails")

Signed-off-by: Dmitry Frolov <frolov@swemel.ru>
Reviewed-by: Michael Tokarev <mjt@tls.msk.ru>
Message-Id: <20230825115818.1091936-1-frolov@swemel.ru>
---
 ui/gtk.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/ui/gtk.c b/ui/gtk.c
index c34c133550..a14d56168d 100644
--- a/ui/gtk.c
+++ b/ui/gtk.c
@@ -2359,7 +2359,7 @@ static void gtk_display_init(DisplayState *ds, DisplayOptions *opts)
 {
     VirtualConsole *vc;
 
-    GtkDisplayState *s = g_malloc0(sizeof(*s));
+    GtkDisplayState *s;
     GdkDisplay *window_display;
     GtkIconTheme *theme;
     char *dir;
@@ -2369,6 +2369,7 @@ static void gtk_display_init(DisplayState *ds, DisplayOptions *opts)
         exit(1);
     }
     assert(opts->type == DISPLAY_TYPE_GTK);
+    s = g_malloc0(sizeof(*s));
     s->opts = opts;
 
     theme = gtk_icon_theme_get_default();
-- 
2.41.0



^ permalink raw reply related	[flat|nested] 54+ messages in thread

* Re: [PULL 00/52] UI patches
  2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
                   ` (51 preceding siblings ...)
  2023-09-04 11:52 ` [PULL 52/52] ui/gtk: fix leaks found wtih fuzzing marcandre.lureau
@ 2023-09-06 18:24 ` Stefan Hajnoczi
  52 siblings, 0 replies; 54+ messages in thread
From: Stefan Hajnoczi @ 2023-09-06 18:24 UTC (permalink / raw)
  To: marcandre.lureau; +Cc: qemu-devel, stefanha, Marc-André Lureau

[-- Attachment #1: Type: text/plain, Size: 115 bytes --]

Applied, thanks.

Please update the changelog at https://wiki.qemu.org/ChangeLog/8.2 for any user-visible changes.

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 488 bytes --]

^ permalink raw reply	[flat|nested] 54+ messages in thread

end of thread, other threads:[~2023-09-06 18:25 UTC | newest]

Thread overview: 54+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2023-09-04 11:51 [PULL 00/52] UI patches marcandre.lureau
2023-09-04 11:51 ` [PULL 01/52] ui: remove qemu_pixman_color() helper marcandre.lureau
2023-09-04 11:51 ` [PULL 02/52] ui: remove qemu_pixman_linebuf_copy() marcandre.lureau
2023-09-04 11:52 ` [PULL 03/52] ui/qmp: move screendump to ui-qmp-cmds.c marcandre.lureau
2023-09-04 11:52 ` [PULL 04/52] ui/vc: replace vc_chr_write() with generic qemu_chr_write() marcandre.lureau
2023-09-04 11:52 ` [PULL 05/52] ui/vc: drop have_text marcandre.lureau
2023-09-04 11:52 ` [PULL 06/52] ui/console: console_select() regardless of have_gfx marcandre.lureau
2023-09-04 11:52 ` [PULL 07/52] ui/console: call dpy_gfx_update() " marcandre.lureau
2023-09-04 11:52 ` [PULL 08/52] ui/console: drop have_gfx marcandre.lureau
2023-09-04 11:52 ` [PULL 09/52] ui/console: get the DisplayState from new_console() marcandre.lureau
2023-09-04 11:52 ` [PULL 10/52] ui/console: new_console() cannot fail marcandre.lureau
2023-09-04 11:52 ` [PULL 11/52] ui/vc: VC always has a DisplayState now marcandre.lureau
2023-09-04 11:52 ` [PULL 12/52] ui/vc: move VCChardev declaration at the top marcandre.lureau
2023-09-04 11:52 ` [PULL 13/52] ui/vc: replace variable with static text attributes default marcandre.lureau
2023-09-04 11:52 ` [PULL 14/52] ui/vc: fold text_update_xy() marcandre.lureau
2023-09-04 11:52 ` [PULL 15/52] ui/vc: pass VCCharDev to VC-specific functions marcandre.lureau
2023-09-04 11:52 ` [PULL 16/52] ui/vc: move VCCharDev specific fields out of QemuConsole marcandre.lureau
2023-09-04 11:52 ` [PULL 17/52] ui/console: use OBJECT_DEFINE_TYPE for QemuConsole marcandre.lureau
2023-09-04 11:52 ` [PULL 18/52] ui/console: change new_console() to use object initialization marcandre.lureau
2023-09-04 11:52 ` [PULL 19/52] ui/console: introduce different console objects marcandre.lureau
2023-09-04 11:52 ` [PULL 20/52] ui/console: instantiate a specific console type marcandre.lureau
2023-09-04 11:52 ` [PULL 21/52] ui/console: register the console from qemu_console_init() marcandre.lureau
2023-09-04 11:52 ` [PULL 22/52] ui/console: remove new_console() marcandre.lureau
2023-09-04 11:52 ` [PULL 23/52] ui/console: specialize console_lookup_unused() marcandre.lureau
2023-09-04 11:52 ` [PULL 24/52] ui/console: update the head from unused QemuConsole marcandre.lureau
2023-09-04 11:52 ` [PULL 25/52] ui/console: allocate ui_timer in QemuConsole marcandre.lureau
2023-09-04 11:52 ` [PULL 26/52] ui/vc: move cursor_timer initialization to QemuTextConsole class marcandre.lureau
2023-09-04 11:52 ` [PULL 27/52] ui/console: free more QemuConsole resources marcandre.lureau
2023-09-04 11:52 ` [PULL 28/52] ui/vc: move text fields to QemuTextConsole marcandre.lureau
2023-09-04 11:52 ` [PULL 29/52] ui/console: move graphic fields to QemuGraphicConsole marcandre.lureau
2023-09-04 11:52 ` [PULL 30/52] ui/vc: fold text_console_do_init() in vc_chr_open() marcandre.lureau
2023-09-04 11:52 ` [PULL 31/52] ui/vc: move some text console initialization to qom handlers marcandre.lureau
2023-09-04 11:52 ` [PULL 32/52] ui/console: simplify getting active_console size marcandre.lureau
2023-09-04 11:52 ` [PULL 33/52] ui/console: remove need for g_width/g_height marcandre.lureau
2023-09-04 11:52 ` [PULL 34/52] ui/vc: use common text console surface creation marcandre.lureau
2023-09-04 11:52 ` [PULL 35/52] ui/console: declare console types in console.h marcandre.lureau
2023-09-04 11:52 ` [PULL 36/52] ui/console: use QEMU_PIXMAN_COLOR helpers marcandre.lureau
2023-09-04 11:52 ` [PULL 37/52] ui/console: rename vga_ functions with qemu_console_ marcandre.lureau
2023-09-04 11:52 ` [PULL 38/52] ui/console: assert(surface) where appropriate marcandre.lureau
2023-09-04 11:52 ` [PULL 39/52] ui/console: fold text_console_update_cursor_timer marcandre.lureau
2023-09-04 11:52 ` [PULL 40/52] ui/vc: skip text console resize when possible marcandre.lureau
2023-09-04 11:52 ` [PULL 41/52] ui/console: minor stylistic changes marcandre.lureau
2023-09-04 11:52 ` [PULL 42/52] ui/vc: move text console invalidate in helper marcandre.lureau
2023-09-04 11:52 ` [PULL 43/52] ui/vc: do not parse VC-specific options in Spice and GTK marcandre.lureau
2023-09-04 11:52 ` [PULL 44/52] ui/vc: change the argument for QemuTextConsole marcandre.lureau
2023-09-04 11:52 ` [PULL 45/52] ui/spice-display: Avoid dynamic stack allocation marcandre.lureau
2023-09-04 11:52 ` [PULL 46/52] ui/vnc-enc-hextile: Use static rather than dynamic length stack array marcandre.lureau
2023-09-04 11:52 ` [PULL 47/52] ui/vnc-enc-tight: Avoid dynamic stack allocation marcandre.lureau
2023-09-04 11:52 ` [PULL 48/52] ui/dbus: Properly dispose touch/mouse dbus objects marcandre.lureau
2023-09-04 11:52 ` [PULL 49/52] ui/dbus: implement damage regions for GL marcandre.lureau
2023-09-04 11:52 ` [PULL 50/52] ui/vdagent: call vdagent_disconnect() when agent connection is lost marcandre.lureau
2023-09-04 11:52 ` [PULL 51/52] ui/vdagent: Unregister input handler of mouse during finalization marcandre.lureau
2023-09-04 11:52 ` [PULL 52/52] ui/gtk: fix leaks found wtih fuzzing marcandre.lureau
2023-09-06 18:24 ` [PULL 00/52] UI patches Stefan Hajnoczi

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).