static void xenfb_update_interval(void *opaque, uint64_t interval) { struct XenFB *xenfb = opaque; if (xenfb->feature_update) { #ifdef XENFB_TYPE_REFRESH_PERIOD if (xenfb_queue_full(xenfb)) { return; } xenfb_send_refresh_period(xenfb, interval); #endif } }
/* Periodic update of display, transmit the refresh interval to the frontend */ static void xenfb_update(void *opaque) { struct xenfb *xenfb = opaque; int period; if (xenfb_queue_full(xenfb)) return; if (xenfb->ds->idle) period = XENFB_NO_REFRESH; else { period = xenfb->ds->gui_timer_interval; if (!period) period = GUI_REFRESH_INTERVAL; } /* Will have to be disabled for frontends without feature-update */ if (xenfb->refresh_period != period) { xenfb_send_refresh_period(xenfb, period); xenfb->refresh_period = period; } }
/* * Periodic update of display. * Also transmit the refresh interval to the frontend. * * Never ever do any qemu display operations * (resize, screen update) outside this function. * Our screen might be inactive. When asked for * an update we know it is active. */ static void xenfb_update(void *opaque) { struct XenFB *xenfb = opaque; struct DisplayChangeListener *l; int i; if (xenfb->c.xendev.be_state != XenbusStateConnected) return; if (xenfb->feature_update) { #ifdef XENFB_TYPE_REFRESH_PERIOD int period = 99999999; int idle = 1; if (xenfb_queue_full(xenfb)) return; for (l = xenfb->c.ds->listeners; l != NULL; l = l->next) { if (l->idle) continue; idle = 0; if (!l->gui_timer_interval) { if (period > GUI_REFRESH_INTERVAL) period = GUI_REFRESH_INTERVAL; } else { if (period > l->gui_timer_interval) period = l->gui_timer_interval; } } if (idle) period = XENFB_NO_REFRESH; if (xenfb->refresh_period != period) { xenfb_send_refresh_period(xenfb, period); xenfb->refresh_period = period; xen_be_printf(&xenfb->c.xendev, 1, "refresh period: %d\n", period); } #else ; /* nothing */ #endif } else { /* we don't get update notifications, thus use the * sledge hammer approach ... */ xenfb->up_fullscreen = 1; } /* resize if needed */ if (xenfb->do_resize) { xenfb->do_resize = 0; switch (xenfb->depth) { case 16: case 32: /* console.c supported depth -> buffer can be used directly */ qemu_free_displaysurface(xenfb->c.ds); xenfb->c.ds->surface = qemu_create_displaysurface_from (xenfb->width, xenfb->height, xenfb->depth, xenfb->row_stride, xenfb->pixels + xenfb->offset); break; default: /* we must convert stuff */ qemu_resize_displaysurface(xenfb->c.ds, xenfb->width, xenfb->height); break; } xen_be_printf(&xenfb->c.xendev, 1, "update: resizing: %dx%d @ %d bpp%s\n", xenfb->width, xenfb->height, xenfb->depth, is_buffer_shared(xenfb->c.ds->surface) ? " (shared)" : ""); dpy_resize(xenfb->c.ds); xenfb->up_fullscreen = 1; } /* run queued updates */ if (xenfb->up_fullscreen) { xen_be_printf(&xenfb->c.xendev, 3, "update: fullscreen\n"); xenfb_guest_copy(xenfb, 0, 0, xenfb->width, xenfb->height); } else if (xenfb->up_count) { xen_be_printf(&xenfb->c.xendev, 3, "update: %d rects\n", xenfb->up_count); for (i = 0; i < xenfb->up_count; i++) xenfb_guest_copy(xenfb, xenfb->up_rects[i].x, xenfb->up_rects[i].y, xenfb->up_rects[i].w, xenfb->up_rects[i].h); } else { xen_be_printf(&xenfb->c.xendev, 3, "update: nothing\n"); } xenfb->up_count = 0; xenfb->up_fullscreen = 0; }