static void image_cache_put(SpiceImageCache *spice_cache, uint64_t id, pixman_image_t *image) { ImageCache *cache = SPICE_UPCAST(ImageCache, spice_cache); ImageCacheItem *item; #ifndef IMAGE_CACHE_AGE if (cache->num_items == IMAGE_CACHE_MAX_ITEMS) { SPICE_VERIFY(SPICE_OFFSETOF(ImageCacheItem, lru_link) == 0); ImageCacheItem *tail = (ImageCacheItem *)ring_get_tail(&cache->lru); spice_assert(tail); image_cache_remove(cache, tail); } #endif item = spice_new(ImageCacheItem, 1); item->id = id; #ifdef IMAGE_CACHE_AGE item->age = cache->age; #else cache->num_items++; #endif item->image = pixman_image_ref(image); ring_item_init(&item->lru_link); item->next = cache->hash_table[item->id % IMAGE_CACHE_HASH_SIZE]; cache->hash_table[item->id % IMAGE_CACHE_HASH_SIZE] = item; ring_add(&cache->lru, &item->lru_link); }
static SpiceGstFrame *create_gst_frame(GstBuffer *buffer, SpiceFrame *frame) { SpiceGstFrame *gstframe = spice_new(SpiceGstFrame, 1); gstframe->timestamp = GST_BUFFER_PTS(buffer); gstframe->frame = frame; gstframe->sample = NULL; return gstframe; }
uint8_t *spice_marshaller_reserve_space(SpiceMarshaller *m, size_t size) { MarshallerItem *item; SpiceMarshallerData *d; uint8_t *res; if (size == 0) { return NULL; } d = m->data; /* Check current item */ item = &m->items[m->n_items - 1]; if (item == d->current_buffer_item && remaining_buffer_size(d) >= size) { assert(m->n_items >= 1); /* We can piggy back on existing item+buffer */ res = item->data + item->len; item->len += size; d->current_buffer_position += size; d->total_size += size; m->total_size += size; return res; } item = spice_marshaller_add_item(m); if (remaining_buffer_size(d) >= size) { /* Fits in current buffer */ item->data = d->current_buffer->data + d->current_buffer_position; item->len = size; d->current_buffer_position += size; d->current_buffer_item = item; } else if (size > MARSHALLER_BUFFER_SIZE / 2) { /* Large item, allocate by itself */ item->data = (uint8_t *)spice_malloc(size); item->len = size; item->free_data = (spice_marshaller_item_free_func)free; item->opaque = NULL; } else { /* Use next buffer */ if (d->current_buffer->next == NULL) { d->current_buffer->next = spice_new(MarshallerBuffer, 1); d->current_buffer->next->next = NULL; } d->current_buffer = d->current_buffer->next; d->current_buffer_position = size; d->current_buffer_item = item; item->data = d->current_buffer->data; item->len = size; } d->total_size += size; m->total_size += size; return item->data; }
SpiceMarshaller *spice_marshaller_get_submarshaller(SpiceMarshaller *m) { SpiceMarshallerData *d; SpiceMarshaller *m2; d = m->data; m2 = spice_new(SpiceMarshaller, 1); spice_marshaller_init(m2, d); d->last_marshaller->next = m2; d->last_marshaller = m2; return m2; }
static MarshallerItem *spice_marshaller_add_item(SpiceMarshaller *m) { MarshallerItem *item; if (m->n_items == m->items_size) { int items_size = m->items_size * 2; if (m->items == m->static_items) { m->items = spice_new(MarshallerItem, items_size); memcpy(m->items, m->static_items, sizeof(MarshallerItem) * m->n_items); } else { m->items = spice_renew(MarshallerItem, m->items, items_size); } m->items_size = items_size; } item = &m->items[m->n_items++]; item->free_data = NULL; return item; }
SpiceMarshaller *spice_marshaller_new(void) { SpiceMarshallerData *d; SpiceMarshaller *m; d = spice_new(SpiceMarshallerData, 1); d->last_marshaller = d->marshallers = &d->static_marshaller; d->total_size = 0; d->base = 0; d->buffers = &d->static_buffer; d->buffers->next = NULL; d->current_buffer = d->buffers; d->current_buffer_position = 0; d->current_buffer_item = NULL; m = &d->static_marshaller; spice_marshaller_init(m, d); return m; }