summaryrefslogtreecommitdiffstats
path: root/server
diff options
context:
space:
mode:
Diffstat (limited to 'server')
-rw-r--r--server/dcc.c90
-rw-r--r--server/dcc.h2
-rw-r--r--server/red_worker.c91
3 files changed, 92 insertions, 91 deletions
diff --git a/server/dcc.c b/server/dcc.c
index 1e188140..9af6d842 100644
--- a/server/dcc.c
+++ b/server/dcc.c
@@ -940,3 +940,93 @@ void dcc_palette_cache_reset(DisplayChannelClient *dcc)
{
red_palette_cache_reset(dcc, CLIENT_PALETTE_CACHE_SIZE);
}
+
+static void dcc_push_release(DisplayChannelClient *dcc, uint8_t type, uint64_t id,
+ uint64_t* sync_data)
+{
+ FreeList *free_list = &dcc->send_data.free_list;
+ int i;
+
+ for (i = 0; i < MAX_CACHE_CLIENTS; i++) {
+ free_list->sync[i] = MAX(free_list->sync[i], sync_data[i]);
+ }
+
+ if (free_list->res->count == free_list->res_size) {
+ SpiceResourceList *new_list;
+ new_list = spice_malloc(sizeof(*new_list) +
+ free_list->res_size * sizeof(SpiceResourceID) * 2);
+ new_list->count = free_list->res->count;
+ memcpy(new_list->resources, free_list->res->resources,
+ new_list->count * sizeof(SpiceResourceID));
+ free(free_list->res);
+ free_list->res = new_list;
+ free_list->res_size *= 2;
+ }
+ free_list->res->resources[free_list->res->count].type = type;
+ free_list->res->resources[free_list->res->count++].id = id;
+}
+
+int dcc_pixmap_cache_unlocked_add(DisplayChannelClient *dcc, uint64_t id,
+ uint32_t size, int lossy)
+{
+ PixmapCache *cache = dcc->pixmap_cache;
+ NewCacheItem *item;
+ uint64_t serial;
+ int key;
+
+ spice_assert(size > 0);
+
+ item = spice_new(NewCacheItem, 1);
+ serial = red_channel_client_get_message_serial(RED_CHANNEL_CLIENT(dcc));
+
+ if (cache->generation != dcc->pixmap_cache_generation) {
+ if (!dcc->pending_pixmaps_sync) {
+ red_channel_client_pipe_add_type(
+ RED_CHANNEL_CLIENT(dcc), PIPE_ITEM_TYPE_PIXMAP_SYNC);
+ dcc->pending_pixmaps_sync = TRUE;
+ }
+ free(item);
+ return FALSE;
+ }
+
+ cache->available -= size;
+ while (cache->available < 0) {
+ NewCacheItem *tail;
+ NewCacheItem **now;
+
+ if (!(tail = (NewCacheItem *)ring_get_tail(&cache->lru)) ||
+ tail->sync[dcc->common.id] == serial) {
+ cache->available += size;
+ free(item);
+ return FALSE;
+ }
+
+ now = &cache->hash_table[BITS_CACHE_HASH_KEY(tail->id)];
+ for (;;) {
+ spice_assert(*now);
+ if (*now == tail) {
+ *now = tail->next;
+ break;
+ }
+ now = &(*now)->next;
+ }
+ ring_remove(&tail->lru_link);
+ cache->items--;
+ cache->available += tail->size;
+ cache->sync[dcc->common.id] = serial;
+ dcc_push_release(dcc, SPICE_RES_TYPE_PIXMAP, tail->id, tail->sync);
+ free(tail);
+ }
+ ++cache->items;
+ item->next = cache->hash_table[(key = BITS_CACHE_HASH_KEY(id))];
+ cache->hash_table[key] = item;
+ ring_item_init(&item->lru_link);
+ ring_add(&cache->lru, &item->lru_link);
+ item->id = id;
+ item->size = size;
+ item->lossy = lossy;
+ memset(item->sync, 0, sizeof(item->sync));
+ item->sync[dcc->common.id] = serial;
+ cache->sync[dcc->common.id] = serial;
+ return TRUE;
+}
diff --git a/server/dcc.h b/server/dcc.h
index 7827f72a..c62c3c90 100644
--- a/server/dcc.h
+++ b/server/dcc.h
@@ -167,6 +167,8 @@ void dcc_palette_cache_reset (DisplayCha
void dcc_palette_cache_palette (DisplayChannelClient *dcc,
SpicePalette *palette,
uint8_t *flags);
+int dcc_pixmap_cache_unlocked_add (DisplayChannelClient *dcc,
+ uint64_t id, uint32_t size, int lossy);
typedef struct compress_send_data_t {
void* comp_buf;
diff --git a/server/red_worker.c b/server/red_worker.c
index 55506288..155d2a2c 100644
--- a/server/red_worker.c
+++ b/server/red_worker.c
@@ -183,8 +183,6 @@ static void red_update_area_till(DisplayChannel *display, const SpiceRect *area,
Drawable *last);
static inline void display_begin_send_message(RedChannelClient *rcc);
static void dcc_release_glz(DisplayChannelClient *dcc);
-static void display_channel_push_release(DisplayChannelClient *dcc, uint8_t type, uint64_t id,
- uint64_t* sync_data);
static int red_display_free_some_independent_glz_drawables(DisplayChannelClient *dcc);
static void dcc_free_glz_drawable(DisplayChannelClient *dcc, RedGlzDrawable *drawable);
static void display_channel_client_release_item_before_push(DisplayChannelClient *dcc,
@@ -2096,70 +2094,6 @@ static int red_display_free_some_independent_glz_drawables(DisplayChannelClient
return n;
}
-int dcc_pixmap_cache_unlocked_add(DisplayChannelClient *dcc, uint64_t id, uint32_t size, int lossy)
-{
- PixmapCache *cache = dcc->pixmap_cache;
- NewCacheItem *item;
- uint64_t serial;
- int key;
-
- spice_assert(size > 0);
-
- item = spice_new(NewCacheItem, 1);
- serial = red_channel_client_get_message_serial(RED_CHANNEL_CLIENT(dcc));
-
- if (cache->generation != dcc->pixmap_cache_generation) {
- if (!dcc->pending_pixmaps_sync) {
- red_channel_client_pipe_add_type(
- RED_CHANNEL_CLIENT(dcc), PIPE_ITEM_TYPE_PIXMAP_SYNC);
- dcc->pending_pixmaps_sync = TRUE;
- }
- free(item);
- return FALSE;
- }
-
- cache->available -= size;
- while (cache->available < 0) {
- NewCacheItem *tail;
- NewCacheItem **now;
-
- if (!(tail = (NewCacheItem *)ring_get_tail(&cache->lru)) ||
- tail->sync[dcc->common.id] == serial) {
- cache->available += size;
- free(item);
- return FALSE;
- }
-
- now = &cache->hash_table[BITS_CACHE_HASH_KEY(tail->id)];
- for (;;) {
- spice_assert(*now);
- if (*now == tail) {
- *now = tail->next;
- break;
- }
- now = &(*now)->next;
- }
- ring_remove(&tail->lru_link);
- cache->items--;
- cache->available += tail->size;
- cache->sync[dcc->common.id] = serial;
- display_channel_push_release(dcc, SPICE_RES_TYPE_PIXMAP, tail->id, tail->sync);
- free(tail);
- }
- ++cache->items;
- item->next = cache->hash_table[(key = BITS_CACHE_HASH_KEY(id))];
- cache->hash_table[key] = item;
- ring_item_init(&item->lru_link);
- ring_add(&cache->lru, &item->lru_link);
- item->id = id;
- item->size = size;
- item->lossy = lossy;
- memset(item->sync, 0, sizeof(item->sync));
- item->sync[dcc->common.id] = serial;
- cache->sync[dcc->common.id] = serial;
- return TRUE;
-}
-
static inline void red_display_add_image_to_pixmap_cache(RedChannelClient *rcc,
SpiceImage *image, SpiceImage *io_image,
int is_lossy)
@@ -3766,31 +3700,6 @@ static inline void red_marshall_qxl_drawable(RedChannelClient *rcc,
}
}
-static void display_channel_push_release(DisplayChannelClient *dcc, uint8_t type, uint64_t id,
- uint64_t* sync_data)
-{
- FreeList *free_list = &dcc->send_data.free_list;
- int i;
-
- for (i = 0; i < MAX_CACHE_CLIENTS; i++) {
- free_list->sync[i] = MAX(free_list->sync[i], sync_data[i]);
- }
-
- if (free_list->res->count == free_list->res_size) {
- SpiceResourceList *new_list;
- new_list = spice_malloc(sizeof(*new_list) +
- free_list->res_size * sizeof(SpiceResourceID) * 2);
- new_list->count = free_list->res->count;
- memcpy(new_list->resources, free_list->res->resources,
- new_list->count * sizeof(SpiceResourceID));
- free(free_list->res);
- free_list->res = new_list;
- free_list->res_size *= 2;
- }
- free_list->res->resources[free_list->res->count].type = type;
- free_list->res->resources[free_list->res->count++].id = id;
-}
-
static inline void display_marshal_sub_msg_inval_list(SpiceMarshaller *m,
FreeList *free_list)
{