static void gs_j_mem_term (j_common_ptr cinfo) { gs_memory_t *cmem = (gs_memory_t *)(GET_CUST_MEM_DATA(cinfo)->priv); gs_memory_t *mem = gs_memory_chunk_target(cmem); gs_memory_chunk_release(cmem); (void)jpeg_cust_mem_set_private(GET_CUST_MEM_DATA(cinfo), mem); }
void clist_teardown_render_threads(gx_device *dev) { gx_device_clist *cldev = (gx_device_clist *)dev; gx_device_clist_common *cdev = (gx_device_clist_common *)dev; gx_device_clist_reader *crdev = &cldev->reader; gs_memory_t *mem = cdev->bandlist_memory, *chunk_base_mem; int i; if (crdev->render_threads != NULL) { chunk_base_mem = gs_memory_chunk_target(crdev->render_threads[0].memory); /* Wait for each thread to finish then free its memory */ for (i = (crdev->num_render_threads - 1); i >= 0; i--) { clist_render_thread_control_t *thread = &(crdev->render_threads[i]); gx_device_clist_common *thread_cdev = (gx_device_clist_common *)thread->cdev; if (thread->status == RENDER_THREAD_BUSY) gx_semaphore_wait(thread->sema_this); gp_thread_finish(thread->thread); thread->thread = NULL; /* Free control semaphores */ gx_semaphore_free(thread->sema_group); gx_semaphore_free(thread->sema_this); /* destroy the thread's buffer device */ thread_cdev->buf_procs.destroy_buf_device(thread->bdev); /* * Free the BufferSpace, close the band files * Note that the BufferSpace is freed using 'ppdev->buf' so the 'data' * pointer doesn't need to be the one that the thread started with */ /* Close the file handles, but don't delete (unlink) the files */ thread_cdev->page_info.io_procs->fclose(thread_cdev->page_bfile, thread_cdev->page_bfname, false); thread_cdev->page_info.io_procs->fclose(thread_cdev->page_cfile, thread_cdev->page_cfname, false); thread_cdev->do_not_open_or_close_bandfiles = true; /* we already closed the files */ gdev_prn_free_memory((gx_device *)thread_cdev); /* Free the device copy this thread used. Note that the deviceN stuff if was allocated and copied earlier for the device will be freed with this call and the icc_struct ref count will be decremented. */ gs_free_object(thread->memory, thread_cdev, "clist_teardown_render_threads"); #ifdef DEBUG if (gs_debug[':']) dprintf2("%% Thread %d total usertime=%ld msec\n", i, thread->cputime); dprintf1("\nthread: %d ending memory state...\n", i); gs_memory_chunk_dump_memory(thread->memory); dprintf(" memory dump done.\n"); #endif gs_memory_chunk_release(thread->memory); } cdev->data = crdev->main_thread_data; /* restore the pointer for writing */ gs_free_object(mem, crdev->render_threads, "clist_teardown_render_threads"); crdev->render_threads = NULL; /* Now re-open the clist temp files so we can write to them */ if (cdev->page_cfile == NULL) { char fmode[4]; strcpy(fmode, "a+"); /* file already exists and we want to re-use it */ strncat(fmode, gp_fmode_binary_suffix, 1); cdev->page_info.io_procs->fopen(cdev->page_cfname, fmode, &cdev->page_cfile, mem, cdev->bandlist_memory, true); cdev->page_info.io_procs->fseek(cdev->page_cfile, 0, SEEK_SET, cdev->page_cfname); cdev->page_info.io_procs->fopen(cdev->page_bfname, fmode, &cdev->page_bfile, mem, cdev->bandlist_memory, false); cdev->page_info.io_procs->fseek(cdev->page_bfile, 0, SEEK_SET, cdev->page_bfname); } } }