/* find_block -- find a free block of specified size */ static header *find_block(unsigned size, unsigned objsize) { header *h = NULL, *h2; int i = min(size/GC_PAGESIZE, BIG_BLOCK); ASSERT(size % GC_PAGESIZE == 0); do { for (headers(h2, free_list[i])) { /* This always succeeds for small blocks, and gives first-fit allocation for big blocks. */ if (size <= h2->h_size) { h = h2; break; } } i++; } while (h == NULL && i <= BIG_BLOCK); if (h == NULL) { /* No suitable block was found. Get a big chunk. */ unsigned chunk = max(size, CHUNK_SIZE); GC_TRACE("[ex]"); ASSERT(chunk % GC_PAGESIZE == 0); h = alloc_header(); h->h_memory = (uchar *) get_memory(chunk); h->h_size = chunk; /* Add to the free list for merging and page table setup */ h = free_block(h, FALSE); } ASSERT(h->h_memory != NULL && h->h_size >= size); unlink(h); if (size < h->h_size) { /* Split the block, and return the waste to the free list. It's best to use header h for the waste: that way, we don't have to reset lots of page table entries when we chip a small piece off a big block. */ h2 = alloc_header(); h2->h_memory = h->h_memory; h2->h_size = size; page_setup(h2->h_memory, size, h2); h->h_memory += size; h->h_size -= size; make_free(h); h = h2; } h->h_objsize = objsize; h->h_epoch = gencount; return h; }
/* free_block -- free a block, merging it with its neighbours */ static header *free_block(header *h, bool mapped) { /* Mapped is true if this memory is being recycled: it's already in the page table, but we'll need to zero it. */ header *prev = left_neighbour(h), *next = right_neighbour(h); /* Base and size of area where page table needs updating */ uchar *pg_memory = h->h_memory; unsigned pg_size = (mapped ? 0 : h->h_size); #ifdef TRACE if (debug['l']) { printf("Freeing block at %p, size %#x\n", h->h_memory, h->h_size); if (prev == NULL) printf("prev=null, "); else printf("prev=%p, ", prev->h_memory); if (next == NULL) printf("next=null\n"); else printf("next=%p\n", next->h_memory); } #endif if (mapped) memset(h->h_memory, 0, h->h_size); if (prev != NULL && prev->h_objsize == 0) { DEBUG_PRINT('l', ("Merging with prev\n")); unlink(prev); prev->h_size += h->h_size; pg_memory = h->h_memory; pg_size = h->h_size; free_header(h); h = prev; } if (next != NULL && next->h_objsize == 0) { DEBUG_PRINT('l', ("Merging with next\n")); unlink(next); next->h_memory = h->h_memory; next->h_size += h->h_size; pg_memory = h->h_memory; pg_size = h->h_size; free_header(h); h = next; } if (pg_size > 0) page_setup(pg_memory, pg_size, h); make_free(h); /* Return the merged block */ return h; }
static void run (const gchar *name, gint nparams, const GimpParam *param, gint *nreturn_vals, GimpParam **return_vals) { static GimpParam values[2]; GimpRunMode run_mode; GimpPDBStatusType status; gint32 image_ID; GError *error = NULL; run_mode = param[0].data.d_int32; INIT_I18N (); *nreturn_vals = 1; *return_vals = values; g_thread_init (NULL); values[0].type = GIMP_PDB_STATUS; values[0].data.d_status = GIMP_PDB_EXECUTION_ERROR; image_ID = param[1].data.d_int32; if (strcmp (name, PRINT_PROC_NAME) == 0) { status = print_image (image_ID, run_mode == GIMP_RUN_INTERACTIVE, &error); if (error && run_mode == GIMP_RUN_INTERACTIVE) { print_show_error (error->message); g_clear_error (&error); } } else if (strcmp (name, PAGE_SETUP_PROC_NAME) == 0) { if (run_mode == GIMP_RUN_INTERACTIVE) { status = page_setup (image_ID); } else { status = GIMP_PDB_CALLING_ERROR; } } else { status = GIMP_PDB_CALLING_ERROR; } if (status != GIMP_PDB_SUCCESS && error) { *nreturn_vals = 2; values[1].type = GIMP_PDB_STRING; values[1].data.d_string = error->message; } values[0].data.d_status = status; }
sheet_state worksheet::sheet_state() const { return page_setup().sheet_state(); }
void worksheet::sheet_state(xlnt::sheet_state state) { page_setup().sheet_state(state); }