Revision 7d964c9d ui/vnc.c
b/ui/vnc.c | ||
---|---|---|
1014 | 1014 |
|
1015 | 1015 |
static void vnc_disconnect_finish(VncState *vs) |
1016 | 1016 |
{ |
1017 |
int i; |
|
1018 |
|
|
1017 | 1019 |
vnc_jobs_join(vs); /* Wait encoding jobs */ |
1018 | 1020 |
|
1019 | 1021 |
vnc_lock_output(vs); |
... | ... | |
1050 | 1052 |
#ifdef CONFIG_VNC_THREAD |
1051 | 1053 |
qemu_mutex_destroy(&vs->output_mutex); |
1052 | 1054 |
#endif |
1055 |
for (i = 0; i < VNC_STAT_ROWS; ++i) { |
|
1056 |
qemu_free(vs->lossy_rect[i]); |
|
1057 |
} |
|
1058 |
qemu_free(vs->lossy_rect); |
|
1053 | 1059 |
qemu_free(vs); |
1054 | 1060 |
} |
1055 | 1061 |
|
... | ... | |
2267 | 2273 |
return &vs->stats[y / VNC_STAT_RECT][x / VNC_STAT_RECT]; |
2268 | 2274 |
} |
2269 | 2275 |
|
2270 |
static void vnc_update_stats(VncDisplay *vd, struct timeval * tv) |
|
2276 |
void vnc_sent_lossy_rect(VncState *vs, int x, int y, int w, int h) |
|
2277 |
{ |
|
2278 |
int i, j; |
|
2279 |
|
|
2280 |
w = (x + w) / VNC_STAT_RECT; |
|
2281 |
h = (y + h) / VNC_STAT_RECT; |
|
2282 |
x /= VNC_STAT_RECT; |
|
2283 |
y /= VNC_STAT_RECT; |
|
2284 |
|
|
2285 |
for (j = y; j <= y + h; j++) { |
|
2286 |
for (i = x; i <= x + w; i++) { |
|
2287 |
vs->lossy_rect[j][i] = 1; |
|
2288 |
} |
|
2289 |
} |
|
2290 |
} |
|
2291 |
|
|
2292 |
static int vnc_refresh_lossy_rect(VncDisplay *vd, int x, int y) |
|
2293 |
{ |
|
2294 |
VncState *vs; |
|
2295 |
int sty = y / VNC_STAT_RECT; |
|
2296 |
int stx = x / VNC_STAT_RECT; |
|
2297 |
int has_dirty = 0; |
|
2298 |
|
|
2299 |
y = y / VNC_STAT_RECT * VNC_STAT_RECT; |
|
2300 |
x = x / VNC_STAT_RECT * VNC_STAT_RECT; |
|
2301 |
|
|
2302 |
QTAILQ_FOREACH(vs, &vd->clients, next) { |
|
2303 |
int j; |
|
2304 |
|
|
2305 |
/* kernel send buffers are full -> refresh later */ |
|
2306 |
if (vs->output.offset) { |
|
2307 |
continue; |
|
2308 |
} |
|
2309 |
|
|
2310 |
if (!vs->lossy_rect[sty][stx]) { |
|
2311 |
continue; |
|
2312 |
} |
|
2313 |
vs->lossy_rect[sty][stx] = 0; |
|
2314 |
for (j = 0; j < VNC_STAT_RECT; ++j) { |
|
2315 |
vnc_set_bits(vs->dirty[y + j], x / 16, VNC_STAT_RECT / 16); |
|
2316 |
} |
|
2317 |
has_dirty++; |
|
2318 |
} |
|
2319 |
return has_dirty; |
|
2320 |
} |
|
2321 |
|
|
2322 |
static int vnc_update_stats(VncDisplay *vd, struct timeval * tv) |
|
2271 | 2323 |
{ |
2272 | 2324 |
int x, y; |
2273 | 2325 |
struct timeval res; |
2326 |
int has_dirty = 0; |
|
2274 | 2327 |
|
2275 | 2328 |
for (y = 0; y < vd->guest.ds->height; y += VNC_STAT_RECT) { |
2276 | 2329 |
for (x = 0; x < vd->guest.ds->width; x += VNC_STAT_RECT) { |
... | ... | |
2283 | 2336 |
timersub(tv, &VNC_REFRESH_STATS, &res); |
2284 | 2337 |
|
2285 | 2338 |
if (timercmp(&vd->guest.last_freq_check, &res, >)) { |
2286 |
return ; |
|
2339 |
return has_dirty;
|
|
2287 | 2340 |
} |
2288 | 2341 |
vd->guest.last_freq_check = *tv; |
2289 | 2342 |
|
... | ... | |
2302 | 2355 |
|
2303 | 2356 |
if (timercmp(&res, &VNC_REFRESH_LOSSY, >)) { |
2304 | 2357 |
rect->freq = 0; |
2358 |
has_dirty += vnc_refresh_lossy_rect(vd, x, y); |
|
2305 | 2359 |
memset(rect->times, 0, sizeof (rect->times)); |
2306 | 2360 |
continue ; |
2307 | 2361 |
} |
... | ... | |
2315 | 2369 |
rect->freq = 1. / rect->freq; |
2316 | 2370 |
} |
2317 | 2371 |
} |
2372 |
return has_dirty; |
|
2318 | 2373 |
} |
2319 | 2374 |
|
2320 | 2375 |
double vnc_update_freq(VncState *vs, int x, int y, int w, int h) |
... | ... | |
2366 | 2421 |
struct timeval tv; |
2367 | 2422 |
|
2368 | 2423 |
gettimeofday(&tv, NULL); |
2369 |
vnc_update_stats(vd, &tv); |
|
2424 |
has_dirty = vnc_update_stats(vd, &tv);
|
|
2370 | 2425 |
|
2371 | 2426 |
/* |
2372 | 2427 |
* Walk through the guest dirty map. |
... | ... | |
2468 | 2523 |
static void vnc_connect(VncDisplay *vd, int csock) |
2469 | 2524 |
{ |
2470 | 2525 |
VncState *vs = qemu_mallocz(sizeof(VncState)); |
2526 |
int i; |
|
2527 |
|
|
2471 | 2528 |
vs->csock = csock; |
2529 |
vs->lossy_rect = qemu_mallocz(VNC_STAT_ROWS * sizeof (*vs->lossy_rect)); |
|
2530 |
for (i = 0; i < VNC_STAT_ROWS; ++i) { |
|
2531 |
vs->lossy_rect[i] = qemu_mallocz(VNC_STAT_COLS * sizeof (uint8_t)); |
|
2532 |
} |
|
2472 | 2533 |
|
2473 | 2534 |
VNC_DEBUG("New client on socket %d\n", csock); |
2474 | 2535 |
dcl->idle = 0; |
Also available in: Unified diff