packet_data* pd_alloc(uint16_t size, uint16_t block_size) { packet_data* pd = NULL; packet_data* next = NULL; while(size) { uint16_t alloc_size = size > block_size ? block_size : size; if (next == NULL) { pd = bget(align_size(sizeof(packet_data) + alloc_size)); next = pd; } else { next->next = bget(align_size(sizeof(packet_data) + alloc_size)); next = next->next; } if (next == NULL) { pd_free(pd); return NULL; } pd->data = (uint8_t*)pd + sizeof(packet_data); pd->next = NULL; pd->size = alloc_size; pd->total_size = size; pd->refs_count = 1; size -= alloc_size; } return pd; }
static bool grow_buffer_if_needed(struct lwan_strbuf *s, size_t size) { if (s->flags & STATIC) { const size_t aligned_size = align_size(max(size + 1, s->used)); if (UNLIKELY(!aligned_size)) return false; char *buffer = malloc(aligned_size); if (UNLIKELY(!buffer)) return false; memcpy(buffer, s->value.static_buffer, s->used); buffer[s->used + 1] = '\0'; s->flags &= ~STATIC; s->value.buffer = buffer; return true; } if (UNLIKELY(!s->used || lwan_nextpow2(s->used) < size)) { const size_t aligned_size = align_size(size + 1); if (UNLIKELY(!aligned_size)) return false; char *buffer = realloc(s->value.buffer, aligned_size); if (UNLIKELY(!buffer)) return false; s->value.buffer = buffer; } return true; }
void* ora_srealloc(void *ptr, size_t size) { void *result; size_t aux_s = 0; int i; for (i = 0; i < *list_c; i++) if (list[i].first_byte_ptr == ptr) { if (align_size(size) <= list[i].size) return ptr; aux_s = list[i].size; } if (aux_s == 0) ereport(ERROR, (errcode(ERRCODE_INTERNAL_ERROR), errmsg("corrupted pointer"), errdetail("Failed while reallocating memory block in shared memory."), errhint("Report this bug to autors."))); if (NULL != (result = ora_salloc(size))) { memcpy(result, ptr, aux_s); ora_sfree(ptr); } return result; }
void* pmem_alloc(size_t size, int *pfd) { int fd; size_t aligned_size; void* base; pmem_region region = { 0, 0 }; int err; if (NULL == pfd) { return NULL; } *pfd = -1; fd = open(PMEM_DEVICE_NAME, O_RDWR); if (INVALID_FD == fd) { LOGE("[PMEM] open %s failed!", PMEM_DEVICE_NAME); goto open_failed; } aligned_size = align_size(size); base = mmap(0, aligned_size, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0); if (MAP_FAILED == base) { LOGE("[PMEM] mmap size %d failed!", aligned_size); goto mmap_failed; } region.len = aligned_size; err = ioctl(fd, PMEM_MAP, ®ion); if (IOCTL_FAILED == err) { LOGE("[PMEM] PMEM_MAP size %d failed!", aligned_size); goto pmem_map_failed; } property_get("pm.dumpstack", p_value, "0"); //if not set, disable by default p_res = atoi(p_value); if (p_res) { LOGE("[PMEM] pmem_alloc: base: 0x%08x, size: %d\n", (int)base, aligned_size); dump_stack_trace(); } *pfd = fd; return base; insert_failed: ioctl(fd, PMEM_UNMAP, ®ion); pmem_map_failed: munmap(base, aligned_size); mmap_failed: close(fd); open_failed: return NULL; }
void Init_Monitor(void) { firm_top = (int) &g_pfnVectors; firm_end = (int) &_etext + (&_edata - &_sdata); firm_end = align_size(firm_end,1024); test_adr0= 0; }
int ofmem_posix_memalign( void **memptr, size_t alignment, size_t size ) { ofmem_t *ofmem = ofmem_arch_get_private(); alloc_desc_t *d, **pp; void *ret; ucell top; phys_addr_t pa; if( !size ) return ENOMEM; if( !ofmem->next_malloc ) ofmem->next_malloc = (char*)ofmem_arch_get_malloc_base(); size = align_size(size + sizeof(alloc_desc_t), alignment); /* look in the freelist */ for( pp=&ofmem->mfree; *pp && (**pp).size < size; pp = &(**pp).next ) { } /* waste at most 4K by taking an entry from the freelist */ if( *pp && (**pp).size > size + 0x1000 ) { /* Alignment should be on physical not virtual address */ pa = va2pa((uintptr_t)*pp + sizeof(alloc_desc_t)); pa = align_ptr(pa, alignment); ret = (void *)pa2va(pa); memset( ret, 0, (**pp).size - sizeof(alloc_desc_t) ); *pp = (**pp).next; *memptr = ret; return 0; } top = ofmem_arch_get_heap_top(); /* Alignment should be on physical not virtual address */ pa = va2pa((uintptr_t)ofmem->next_malloc + sizeof(alloc_desc_t)); pa = align_ptr(pa, alignment); ret = (void *)pa2va(pa); if( pointer2cell(ret) + size > top ) { printk("out of malloc memory (%x)!\n", size ); return ENOMEM; } d = (alloc_desc_t*)((uintptr_t)ret - sizeof(alloc_desc_t)); ofmem->next_malloc += size; d->next = NULL; d->size = size; memset( ret, 0, size - sizeof(alloc_desc_t) ); *memptr = ret; return 0; }
void Init_Monitor(void) { #if 0 firm_top = (int) &g_pfnVectors; firm_end = (int) &_etext + (&_edata - &_sdata); #endif firm_top = (int) &__cs3_stm32_vector_table; firm_end = (int) &_etext + (&_edata - &__cs3_region_start_ram); firm_end = align_size(firm_end,1024); test_adr0= 0; }
bool space_try_alloc(space_t *space, size_t size, address_t *memory_out) { CHECK_FALSE("allocating in empty space", space_is_empty(space)); size_t aligned = align_size(kValueSize, size); address_t addr = space->next_free; address_t next = addr + aligned; if (next <= space->limit) { // Clear the newly allocated memory to a different value, again to make the // contents recognizable. memset(addr, kAllocedHeapMarker, aligned); *memory_out = addr; space->next_free = next; return true; } else { return false; } }
void *valloc(size_t size) { size_t s = alloc_size(size); void *d = VirtualAlloc(0, s, MEM_RESERVE, PAGE_NOACCESS); if (!d || !VirtualAlloc(d, s - PAGE_SIZE, MEM_COMMIT, PAGE_READWRITE)) { Debug("valloc error(%x %d %d)\n", d, s, size); return NULL; } ((DWORD *)d)[0] = VALLOC_SIG; ((size_t *)d)[1] = size; Debug("valloc (%x %d %d)\n", d, s, size); return (void *)((u_char *)d + s - PAGE_SIZE - align_size(size, ALLOC_ALIGN)); }
void GrVkMemory::FreeImageMemory(const GrVkGpu* gpu, bool linearTiling, const GrVkAlloc& alloc) { GrVkHeap* heap; if (linearTiling) { heap = gpu->getHeap(GrVkGpu::kLinearImage_Heap); } else if (alloc.fSize <= kMaxSmallImageSize) { heap = gpu->getHeap(GrVkGpu::kSmallOptimalImage_Heap); } else { heap = gpu->getHeap(GrVkGpu::kOptimalImage_Heap); } if (!heap->free(alloc)) { // must be an adopted allocation GR_VK_CALL(gpu->vkInterface(), FreeMemory(gpu->device(), alloc.fMemory, nullptr)); } else { gTotalImageMemory -= alloc.fSize; VkDeviceSize pageAlignedSize = align_size(alloc.fSize, kMinVulkanPageSize); gTotalImageMemoryFullPage -= pageAlignedSize; } }
packet_data* data_block_alloc(uint16_t size) { if (size == 0) { return NULL; } packet_data* block = bget(align_size(sizeof(packet_data) + size)); if (block == NULL) { return NULL; } block->data = (uint8_t*)block + sizeof(packet_data); block->next = NULL; block->size = size; block->total_size = size; return block; }
laser_packet* lp_alloc(packet_data* data) { if (data == NULL) { return NULL; } uint16_t aligned_size = align_size(sizeof(laser_packet)); laser_packet* lp = bgetz(aligned_size); if (lp == NULL) { return NULL; } lp->data = data; lp->data_size = data->total_size; return lp; }
bg_shm_t * bg_shm_alloc_read(int id, int size) { void * addr; bg_shm_t * ret = NULL; int shm_fd; char name[SHM_NAME_MAX]; int real_size = get_real_size(size); gen_name(id, name); shm_fd = shm_open(name, O_RDWR, 0); if(shm_fd < 0) { bg_log(BG_LOG_ERROR, LOG_DOMAIN, "shm_open of %s failed: %s", name, strerror(errno)); goto fail; } if((addr = mmap(0, real_size, PROT_READ | PROT_WRITE, MAP_SHARED, shm_fd, 0)) == MAP_FAILED) { bg_log(BG_LOG_ERROR, LOG_DOMAIN, "mmap failed: %s", strerror(errno)); goto fail; } ret = calloc(1, sizeof(*ret)); ret->addr = addr; ret->size = size; ret->rc = (refcounter_t*)(ret->addr + align_size(size)); ret->id = id; bg_log(BG_LOG_DEBUG, LOG_DOMAIN, "created shm segment (read) %s", name); fail: if(shm_fd >= 0) close(shm_fd); return ret; }
int pmem_free(void *ptr, size_t size, int fd) { int err, ret = 0; size_t aligned_size = align_size(size); pmem_region region = { 0, aligned_size }; err = ioctl(fd, PMEM_UNMAP, ®ion); if (IOCTL_FAILED == err) { LOGE("PMEM_UNMAP size %d failed!", size); ret = err; } err = munmap(ptr, aligned_size); if (UNMAP_FAILED == err) { LOGE("mumap size %d failed!", size); ret = err; } err = close(fd); if (CLOSE_FAILED == err) { LOGE("Close file %d failed!", fd); ret = err; } property_get("pm.dumpstack", p_value, "0"); //if not set, disable by default p_res = atoi(p_value); if (p_res) { LOGE("[PMEM] pmem_free: base: 0x%08x, size: %d\n", (int)ptr, aligned_size); dump_stack_trace(); } return ret; }
t_bool buffer_reserve(t_buffer *buf, size_t avail) { char *tmp; size_t target_len; size_t target_size; target_len = buf->len + avail; if (target_len + 1 <= buf->_size) return (true); else { target_size = align_size(target_len + 1, BUFFER_BASE_SIZE); tmp = malloc(target_size); if (tmp == NULL) return (false); ft_strcpy(tmp, buf->str); free(buf->str); buf->str = tmp; buf->_size = target_size; return (true); } }
/** * Create a memory pool descriptor. * 1. If required, set the allocation size to a power of 2 of the element size. * 2. Save the given parameters in the pool descriptor, to be used by * pool_alloc(); * 3. Chain the pool descriptor to the given pool_list, so it can be * automatically freed. */ Pool_desc *pool_new(const char *func, const char *name, size_t num_elements, size_t element_size, bool zero_out, bool align, bool exact) { Pool_desc *mp = malloc(sizeof(Pool_desc)); mp->func = func; mp->name = name; if (align) { mp->element_size = align_size(element_size); mp->alignment = MAX(MIN_ALIGNMENT, mp->element_size); mp->alignment = MIN(MAX_ALIGNMENT, mp->alignment); mp->data_size = num_elements * mp->element_size; mp->block_size = ALIGN(mp->data_size + FLDSIZE_NEXT, mp->alignment); } else { mp->element_size = element_size; mp->alignment = MIN_ALIGNMENT; mp->data_size = num_elements * mp->element_size; mp->block_size = mp->data_size + FLDSIZE_NEXT; } mp->zero_out = zero_out; mp->exact = exact; mp->alloc_next = NULL; mp->chain = NULL; mp->ring = NULL; mp->free_list = NULL; mp->curr_elements = 0; mp->num_elements = num_elements; lgdebug(+D_MEMPOOL, "%sElement size %zu, alignment %zu (pool '%s' created in %s())\n", POOL_ALLOCATOR?"":"(Fake pool allocator) ", mp->element_size, mp->alignment, mp->name, mp->func); return mp; }
bool GrVkHeap::singleAlloc(VkDeviceSize size, VkDeviceSize alignment, uint32_t memoryTypeIndex, GrVkAlloc* alloc) { VkDeviceSize alignedSize = align_size(size, alignment); // first try to find an unallocated subheap that fits our allocation request int bestFitIndex = -1; VkDeviceSize bestFitSize = 0x7FFFFFFF; for (auto i = 0; i < fSubHeaps.count(); ++i) { if (fSubHeaps[i]->memoryTypeIndex() == memoryTypeIndex && fSubHeaps[i]->unallocated()) { VkDeviceSize heapSize = fSubHeaps[i]->size(); if (heapSize >= alignedSize && heapSize < bestFitSize) { bestFitIndex = i; bestFitSize = heapSize; } } } if (bestFitIndex >= 0) { SkASSERT(fSubHeaps[bestFitIndex]->alignment() == alignment); if (fSubHeaps[bestFitIndex]->alloc(size, alloc)) { fUsedSize += alloc->fSize; return true; } return false; } // need to allocate a new subheap SkAutoTDelete<GrVkSubHeap>& subHeap = fSubHeaps.push_back(); subHeap.reset(new GrVkSubHeap(fGpu, memoryTypeIndex, alignedSize, alignment)); fAllocSize += alignedSize; if (subHeap->alloc(size, alloc)) { fUsedSize += alloc->fSize; return true; } return false; }
bg_shm_t * bg_shm_alloc_write(int size) { int shm_fd = -1; void * addr; bg_shm_t * ret = NULL; char name[SHM_NAME_MAX]; int id = 0; pthread_mutexattr_t attr; int real_size = get_real_size(size); while(1) { id++; gen_name(id, name); if((shm_fd = shm_open(name, O_RDWR | O_CREAT | O_EXCL, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)) < 0) { if(errno != EEXIST) { bg_log(BG_LOG_ERROR, LOG_DOMAIN, "shm_open of %s failed: %s", name, strerror(errno)); return NULL; } } else break; } if(ftruncate(shm_fd, real_size)) { bg_log(BG_LOG_ERROR, LOG_DOMAIN, "ftruncate failed: %s", strerror(errno)); goto fail; } if((addr = mmap(0, real_size, PROT_READ | PROT_WRITE, MAP_SHARED, shm_fd, 0)) == MAP_FAILED) { bg_log(BG_LOG_ERROR, LOG_DOMAIN, "mmap failed: %s", strerror(errno)); return NULL; } ret = calloc(1, sizeof(*ret)); ret->addr = addr; ret->size = size; ret->id = id; ret->wr = 1; ret->rc = (refcounter_t*)(ret->addr + align_size(size)); /* Initialize process shared mutex */ pthread_mutexattr_init(&attr); if(pthread_mutexattr_setpshared(&attr, PTHREAD_PROCESS_SHARED)) { bg_log(BG_LOG_ERROR, LOG_DOMAIN, "cannot create process shared mutex: %s", strerror(errno)); goto fail; } pthread_mutex_init(&ret->rc->mutex, &attr); bg_log(BG_LOG_DEBUG, LOG_DOMAIN, "created shm segment (write) %s", name); ret->rc->refcount = 0; fail: close(shm_fd); return ret; }
void Save::save(const Image & in, const Image_Io_Frame_Info & frame) throw (Error) { //DJV_DEBUG("Save::save"); //DJV_DEBUG_PRINT("in = " << in); // Open the file. _open(_file.get(frame.frame)); // Convert the image. const Pixel_Data * p = ∈ if (in.info() != _info) { //DJV_DEBUG_PRINT("convert = " << _image); _image.zero(); Gl_Image::copy(in, _image); p = &_image; } // Write the file. const int w = p->w(), h = p->h(); const int channels = Pixel::channels(p->info().pixel); const int channel_bytes = Pixel::channel_bytes(p->info().pixel); const int bytes = Pixel::bytes(p->info().pixel); bool compress = _options.compression ? true : false; uint32_t length = 0; //DJV_DEBUG_PRINT("channels = " << channels); //DJV_DEBUG_PRINT("channel_bytes = " << channel_bytes); //DJV_DEBUG_PRINT("bytes = " << bytes); size_t pos = 0; pos = _io.position(); //DJV_DEBUG_PRINT("position = " << static_cast<int>(pos)); // 'FOR4' type _io.set_u8('F'); _io.set_u8('O'); _io.set_u8('R'); _io.set_u8('4'); // 'FOR4' length // NOTE: only reserved for now. _io.set_u32(length); // 'TBMP' type _io.set_u8('T'); _io.set_u8('B'); _io.set_u8('M'); _io.set_u8('P'); // Write tiles. V2i size = tile_size (w, h); // Y order. for (int y = 0; y < size.y; y++) { // X order. for (int x = 0; x < size.x; x++) { // Set tile coordinates. uint16_t xmin, xmax, ymin, ymax; // Set xmin and xmax. xmin = x * tile_width(); xmax = Math::min(xmin + tile_width(), w) - 1; // Set ymin and ymax. ymin = y * tile_height(); ymax = Math::min(ymin + tile_height(), h) - 1; // Set width and height. uint32_t tw = xmax - xmin + 1; uint32_t th = ymax - ymin + 1; // Set type. _io.set_u8('R'); _io.set_u8('G'); _io.set_u8('B'); _io.set_u8('A'); // Length. uint32_t length = tw * th * bytes; // Tile length. uint32_t tile_length = length; // Align. length = align_size(length, 4); // Append xmin, xmax, ymin and ymax. length += 8; // Tile compression. bool tile_compress = compress; // Set bytes. Memory_Buffer<uint8_t> tile(tile_length); uint8_t * out_p = tile(); // Handle 8-bit data. if (p->info().pixel == Pixel::RGB_U8 || p->info().pixel == Pixel::RGBA_U8) { if (tile_compress) { uint32_t index = 0, size = 0; // Set bytes. // NOTE: prevent buffer overrun. Memory_Buffer<uint8_t> tmp(tile_length * 2); // Map: RGB(A)8 RGBA to BGRA for (int c = (channels * channel_bytes) - 1; c >= 0; --c) { Memory_Buffer<uint8_t> in(tw * th); uint8_t * in_p = in(); // Data. for (uint16_t py = ymin; py <= ymax; py++) { const uint8_t * in_dy = p->data(0, py); for (uint16_t px = xmin; px <= xmax; px++) { // Get pixel. uint8_t pixel; const uint8_t * in_dx = in_dy + px * bytes + c; Memory::copy(in_dx, &pixel, 1); // Set pixel. *in_p++ = pixel; } } // Compress size = rle_save(in(), tmp() + index, tw * th); index += size; } // If size exceeds tile length use uncompressed. if (index < tile_length) { Memory::copy(tmp(), tile(), index); // Set tile length. tile_length = index; // Append xmin, xmax, ymin and ymax. length = index + 8; // Set length. uint32_t align = align_size(length, 4); if (align > length) { out_p = tile() + index; // Pad. for (int i = 0; i < static_cast<int>(align - length); i++) { *out_p++ = '\0'; tile_length++; } } } else { tile_compress = false; } } if (!tile_compress) { for (uint16_t py = ymin; py <= ymax; py++) { const uint8_t * in_dy = p->data(0, py); for (uint16_t px = xmin; px <= xmax; px++) { // Map: RGB(A)8 RGBA to BGRA for (int c = channels - 1; c >= 0; --c) { // Get pixel. uint8_t pixel; const uint8_t * in_dx = in_dy + px * bytes + c * channel_bytes; Memory::copy(in_dx, &pixel, 1); // Set pixel. *out_p++ = pixel; } } } } } // Handle 16-bit data. else if ( p->info().pixel == Pixel::RGB_U16 || p->info().pixel == Pixel::RGBA_U16) { if (tile_compress) { uint32_t index = 0, size = 0; // Set bytes. // NOTE: prevent buffer overrun. Memory_Buffer<uint8_t> tmp(tile_length * 2); // Set map. int* map = NULL; if (Memory::endian () == Memory::LSB) { int rgb16[] = { 0, 2, 4, 1, 3, 5 }; int rgba16[] = { 0, 2, 4, 7, 1, 3, 5, 6 }; if (_info.pixel == Pixel::RGB_U16) { map = rgb16; } else { map = rgba16; } } else { int rgb16[] = { 1, 3, 5, 0, 2, 4 }; int rgba16[] = { 1, 3, 5, 7, 0, 2, 4, 6 }; if (_info.pixel == Pixel::RGB_U16) { map = rgb16; } else { map = rgba16; } } // Map: RGB(A)16 RGBA to BGRA for (int c = (channels * channel_bytes) - 1; c >= 0; --c) { int mc = map[c]; Memory_Buffer<uint8_t> in(tw * th); uint8_t * in_p = in(); // Data. for (uint16_t py = ymin; py <= ymax; py++) { const uint8_t * in_dy = p->data(0, py); for (uint16_t px = xmin; px <= xmax; px++) { // Get pixel. uint8_t pixel; const uint8_t * in_dx = in_dy + px * bytes + mc; Memory::copy(in_dx, &pixel, 1); // Set pixel. *in_p++ = pixel; } } // Compress size = rle_save(in(), tmp() + index, tw * th); index += size; } // If size exceeds tile length use uncompressed. if (index < tile_length) { Memory::copy(tmp(), tile(), index); // Set tile length. tile_length = index; // Append xmin, xmax, ymin and ymax. length = index + 8; // Set length. uint32_t align = align_size(length, 4); if (align > length) { out_p = tile() + index; // Pad. for ( int i = 0; i < static_cast<int>(align - length); i++) { *out_p++ = '\0'; tile_length++; } } } else { tile_compress = false; } } if (!tile_compress) { for (uint16_t py = ymin; py <= ymax; py++) { const uint8_t * in_dy = p->data(0, py); for (uint16_t px = xmin; px <= xmax; px++) { // Map: RGB(A)16 RGBA to BGRA for (int c = channels - 1; c >= 0; --c) { uint16_t pixel; const uint8_t * in_dx = in_dy + px * bytes + c * channel_bytes; if (Memory::endian () == Memory::LSB) { Memory::endian(in_dx, &pixel, 1, 2); } else { Memory::copy(in_dx, &pixel, 2); } // Set pixel. *out_p++ = pixel; out_p++; } } } } } // Set length. _io.set_u32(length); // Set xmin, xmax, ymin and ymax. _io.set_u16(xmin); _io.set_u16(ymin); _io.set_u16(xmax); _io.set_u16(ymax); // Write. _io.set(tile(), tile_length); } } // Set FOR4 CIMG and FOR4 TBMP size uint32_t p0 = _io.position() - 8; uint32_t p1 = p0 - pos; // NOTE: FOR4 <size> CIMG _io.position (4); _io.set_u32 (p0); // NOTE: FOR4 <size> TBMP _io.position (pos + 4); _io.set_u32 (p1); _io.close(); }
void* ora_salloc(size_t size) { size_t aligned_size; int repeat_c; void *ptr = NULL; aligned_size = align_size(size); for (repeat_c = 0; repeat_c < 2; repeat_c++) { size_t max_min = max_size; int select = -1; int i; /* find first good free block */ for (i = 0; i < *list_c; i++) { if (list[i].dispossible) { /* If this block is just the right size, return it */ if (list[i].size == aligned_size) { list[i].dispossible = false; ptr = list[i].first_byte_ptr; /* list[i].context = context; */ return ptr; } if (list[i].size > aligned_size && list[i].size < max_min) { max_min = list[i].size; select = i; } } } /* If no suitable free slot found, defragment and try again. */ if (select == -1 || *list_c == LIST_ITEMS) { defragmentation(); continue; } /* * A slot larger than required was found. Divide it to avoid wasting * space, and return the slot of the right size. */ list[*list_c].size = list[select].size - aligned_size; list[*list_c].first_byte_ptr = (char*)list[select].first_byte_ptr + aligned_size; list[*list_c].dispossible = true; list[select].size = aligned_size; list[select].dispossible = false; /* list[select].context = context; */ ptr = list[select].first_byte_ptr; *list_c += 1; break; } return ptr; }
void display(void) { struct timeval time1, time2; double total_time, rate, pixel_rate; const unsigned pixel_size = formats[cur_format].num_comp * types[cur_type].byte_size / types[cur_type].num_comp; const unsigned buf_size = align_size(screen_width * pixel_size, ALIGNMENT) * screen_height; unsigned char* buf = (unsigned char*) malloc(buf_size); assert(buf); if (stabilizing_rounds) { printf("Stabilizing round %i\n", stabilizing_rounds); } glPixelStorei(GL_PACK_ALIGNMENT, ALIGNMENT); gettimeofday(&time1, NULL); for (int i = 0; i < NUM_READBACKS; ++i) { glReadPixels(0, 0, screen_width, screen_height, formats[cur_format].format, types[cur_type].type, buf); } gettimeofday(&time2, NULL); total_time = (time2.tv_sec + 1e-6 * time2.tv_usec - time1.tv_sec - 1e-6 * time1.tv_usec); rate = 1e-6 * NUM_READBACKS * buf_size / total_time; pixel_rate = 1e-6 * NUM_READBACKS * screen_width * screen_height / total_time; if (stabilizing_rounds) { --stabilizing_rounds; } else { results[cur_type * NUM_FORMATS + cur_format].type = cur_type; results[cur_type * NUM_FORMATS + cur_format].format = cur_format; results[cur_type * NUM_FORMATS + cur_format].rate = rate; results[cur_type * NUM_FORMATS + cur_format].pixel_rate = pixel_rate; printf("%s %s %g MB/s %g Mp/s\n", formats[cur_format].desc, types[cur_type].desc, rate, pixel_rate); /* Find the next type that is compatible with the current format */ do { ++cur_type; } while (!compatible(formats[cur_format], types[cur_type]) && cur_type < NUM_TYPES); /* Go to the next type/format */ if (cur_type == NUM_TYPES) { cur_type = 0; if (++cur_format == NUM_FORMATS) { printf("\nSorted by data rate:\n"); qsort(results, NUM_FORMATS * NUM_TYPES, sizeof(result_t), compare_data_rate); for (int i = 0; i < NUM_FORMATS * NUM_TYPES; ++i) { if (results[i].rate >= 0) printf("%s %s %g MB/s\n", formats[results[i].format].desc, types[results[i].type].desc, results[i].rate); } printf("\nSorted by pixel rate:\n"); qsort(results, NUM_FORMATS * NUM_TYPES, sizeof(result_t), compare_pixel_rate); for (int i = 0; i < NUM_FORMATS * NUM_TYPES; ++i) { if (results[i].rate >= 0) printf("%s %s %g Mp/s\n", formats[results[i].format].desc, types[results[i].type].desc, results[i].pixel_rate); } exit(0); } } } free(buf); glutReportErrors(); glutPostRedisplay(); }
struct rte_hash * rte_hash_create(const struct rte_hash_parameters *params) { struct rte_hash *h = NULL; uint32_t num_buckets, sig_bucket_size, key_size, hash_tbl_size, sig_tbl_size, key_tbl_size, mem_size; char hash_name[RTE_HASH_NAMESIZE]; struct rte_hash_list *hash_list; /* check that we have an initialised tail queue */ if ((hash_list = RTE_TAILQ_LOOKUP_BY_IDX(RTE_TAILQ_HASH, rte_hash_list)) == NULL) { rte_errno = E_RTE_NO_TAILQ; return NULL; } /* Check for valid parameters */ if ((params == NULL) || (params->entries > RTE_HASH_ENTRIES_MAX) || (params->bucket_entries > RTE_HASH_BUCKET_ENTRIES_MAX) || (params->entries < params->bucket_entries) || !rte_is_power_of_2(params->entries) || !rte_is_power_of_2(params->bucket_entries) || (params->key_len == 0) || (params->key_len > RTE_HASH_KEY_LENGTH_MAX)) { rte_errno = EINVAL; RTE_LOG(ERR, HASH, "rte_hash_create has invalid parameters\n"); return NULL; } rte_snprintf(hash_name, sizeof(hash_name), "HT_%s", params->name); /* Calculate hash dimensions */ num_buckets = params->entries / params->bucket_entries; sig_bucket_size = align_size(params->bucket_entries * sizeof(hash_sig_t), SIG_BUCKET_ALIGNMENT); key_size = align_size(params->key_len, KEY_ALIGNMENT); hash_tbl_size = align_size(sizeof(struct rte_hash), CACHE_LINE_SIZE); sig_tbl_size = align_size(num_buckets * sig_bucket_size, CACHE_LINE_SIZE); key_tbl_size = align_size(num_buckets * key_size * params->bucket_entries, CACHE_LINE_SIZE); /* Total memory required for hash context */ mem_size = hash_tbl_size + sig_tbl_size + key_tbl_size; rte_rwlock_write_lock(RTE_EAL_TAILQ_RWLOCK); /* guarantee there's no existing */ TAILQ_FOREACH(h, hash_list, next) { if (strncmp(params->name, h->name, RTE_HASH_NAMESIZE) == 0) break; } if (h != NULL) goto exit; h = (struct rte_hash *)rte_zmalloc_socket(hash_name, mem_size, CACHE_LINE_SIZE, params->socket_id); if (h == NULL) { RTE_LOG(ERR, HASH, "memory allocation failed\n"); goto exit; } /* Setup hash context */ rte_snprintf(h->name, sizeof(h->name), "%s", params->name); h->entries = params->entries; h->bucket_entries = params->bucket_entries; h->key_len = params->key_len; h->hash_func_init_val = params->hash_func_init_val; h->num_buckets = num_buckets; h->bucket_bitmask = h->num_buckets - 1; h->sig_msb = 1 << (sizeof(hash_sig_t) * 8 - 1); h->sig_tbl = (uint8_t *)h + hash_tbl_size; h->sig_tbl_bucket_size = sig_bucket_size; h->key_tbl = h->sig_tbl + sig_tbl_size; h->key_tbl_key_size = key_size; h->hash_func = (params->hash_func == NULL) ? DEFAULT_HASH_FUNC : params->hash_func; TAILQ_INSERT_TAIL(hash_list, h, next); exit: rte_rwlock_write_unlock(RTE_EAL_TAILQ_RWLOCK); return h; }
inline size_t alloc_size(size_t size) { return align_size((align_size(size, ALLOC_ALIGN) + 16 + PAGE_SIZE), PAGE_SIZE); }
bool GrVkFreeListAlloc::alloc(VkDeviceSize requestedSize, VkDeviceSize* allocOffset, VkDeviceSize* allocSize) { VkDeviceSize alignedSize = align_size(requestedSize, fAlignment); // find the smallest block big enough for our allocation FreeList::Iter iter = fFreeList.headIter(); FreeList::Iter bestFitIter; VkDeviceSize bestFitSize = fSize + 1; VkDeviceSize secondLargestSize = 0; VkDeviceSize secondLargestOffset = 0; while (iter.get()) { Block* block = iter.get(); // need to adjust size to match desired alignment SkASSERT(align_size(block->fOffset, fAlignment) - block->fOffset == 0); if (block->fSize >= alignedSize && block->fSize < bestFitSize) { bestFitIter = iter; bestFitSize = block->fSize; } if (secondLargestSize < block->fSize && block->fOffset != fLargestBlockOffset) { secondLargestSize = block->fSize; secondLargestOffset = block->fOffset; } iter.next(); } SkASSERT(secondLargestSize <= fLargestBlockSize); Block* bestFit = bestFitIter.get(); if (bestFit) { SkASSERT(align_size(bestFit->fOffset, fAlignment) == bestFit->fOffset); *allocOffset = bestFit->fOffset; *allocSize = alignedSize; // adjust or remove current block VkDeviceSize originalBestFitOffset = bestFit->fOffset; if (bestFit->fSize > alignedSize) { bestFit->fOffset += alignedSize; bestFit->fSize -= alignedSize; if (fLargestBlockOffset == originalBestFitOffset) { if (bestFit->fSize >= secondLargestSize) { fLargestBlockSize = bestFit->fSize; fLargestBlockOffset = bestFit->fOffset; } else { fLargestBlockSize = secondLargestSize; fLargestBlockOffset = secondLargestOffset; } } #ifdef SK_DEBUG VkDeviceSize largestSize = 0; iter = fFreeList.headIter(); while (iter.get()) { Block* block = iter.get(); if (largestSize < block->fSize) { largestSize = block->fSize; } iter.next(); } SkASSERT(largestSize == fLargestBlockSize); #endif } else { SkASSERT(bestFit->fSize == alignedSize); if (fLargestBlockOffset == originalBestFitOffset) { fLargestBlockSize = secondLargestSize; fLargestBlockOffset = secondLargestOffset; } fFreeList.remove(bestFit); #ifdef SK_DEBUG VkDeviceSize largestSize = 0; iter = fFreeList.headIter(); while (iter.get()) { Block* block = iter.get(); if (largestSize < block->fSize) { largestSize = block->fSize; } iter.next(); } SkASSERT(largestSize == fLargestBlockSize); #endif } fFreeSize -= alignedSize; SkASSERT(*allocSize > 0); return true; } SkDebugf("Can't allocate %d bytes, %d bytes available, largest free block %d\n", alignedSize, fFreeSize, fLargestBlockSize); return false; }
static int get_real_size(int size) { return align_size(size) + sizeof(refcounter_t); }
bool GrVkMemory::AllocAndBindImageMemory(const GrVkGpu* gpu, VkImage image, bool linearTiling, GrVkAlloc* alloc) { const GrVkInterface* iface = gpu->vkInterface(); VkDevice device = gpu->device(); VkMemoryRequirements memReqs; GR_VK_CALL(iface, GetImageMemoryRequirements(device, image, &memReqs)); uint32_t typeIndex = 0; GrVkHeap* heap; if (linearTiling) { VkMemoryPropertyFlags desiredMemProps = VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT | VK_MEMORY_PROPERTY_HOST_CACHED_BIT; if (!get_valid_memory_type_index(gpu->physicalDeviceMemoryProperties(), memReqs.memoryTypeBits, desiredMemProps, &typeIndex)) { // this memory type should always be available SkASSERT_RELEASE(get_valid_memory_type_index(gpu->physicalDeviceMemoryProperties(), memReqs.memoryTypeBits, VK_MEMORY_PROPERTY_HOST_VISIBLE_BIT | VK_MEMORY_PROPERTY_HOST_COHERENT_BIT, &typeIndex)); } heap = gpu->getHeap(GrVkGpu::kLinearImage_Heap); } else { // this memory type should always be available SkASSERT_RELEASE(get_valid_memory_type_index(gpu->physicalDeviceMemoryProperties(), memReqs.memoryTypeBits, VK_MEMORY_PROPERTY_DEVICE_LOCAL_BIT, &typeIndex)); if (memReqs.size <= kMaxSmallImageSize) { heap = gpu->getHeap(GrVkGpu::kSmallOptimalImage_Heap); } else { heap = gpu->getHeap(GrVkGpu::kOptimalImage_Heap); } } if (!heap->alloc(memReqs.size, memReqs.alignment, typeIndex, alloc)) { SkDebugf("Failed to alloc image\n"); return false; } // Bind Memory to device VkResult err = GR_VK_CALL(iface, BindImageMemory(device, image, alloc->fMemory, alloc->fOffset)); if (err) { SkASSERT_RELEASE(heap->free(*alloc)); return false; } gTotalImageMemory += alloc->fSize; VkDeviceSize pageAlignedSize = align_size(alloc->fSize, kMinVulkanPageSize); gTotalImageMemoryFullPage += pageAlignedSize; return true; }
bool GrVkHeap::subAlloc(VkDeviceSize size, VkDeviceSize alignment, uint32_t memoryTypeIndex, GrVkAlloc* alloc) { VkDeviceSize alignedSize = align_size(size, alignment); // if requested is larger than our subheap allocation, just alloc directly if (alignedSize > fSubHeapSize) { VkMemoryAllocateInfo allocInfo = { VK_STRUCTURE_TYPE_MEMORY_ALLOCATE_INFO, // sType NULL, // pNext size, // allocationSize memoryTypeIndex, // memoryTypeIndex }; VkResult err = GR_VK_CALL(fGpu->vkInterface(), AllocateMemory(fGpu->device(), &allocInfo, nullptr, &alloc->fMemory)); if (VK_SUCCESS != err) { return false; } alloc->fOffset = 0; alloc->fSize = 0; // hint that this is not a subheap allocation return true; } // first try to find a subheap that fits our allocation request int bestFitIndex = -1; VkDeviceSize bestFitSize = 0x7FFFFFFF; for (auto i = 0; i < fSubHeaps.count(); ++i) { if (fSubHeaps[i]->memoryTypeIndex() == memoryTypeIndex) { VkDeviceSize heapSize = fSubHeaps[i]->largestBlockSize(); if (heapSize >= alignedSize && heapSize < bestFitSize) { bestFitIndex = i; bestFitSize = heapSize; } } } if (bestFitIndex >= 0) { SkASSERT(fSubHeaps[bestFitIndex]->alignment() == alignment); if (fSubHeaps[bestFitIndex]->alloc(size, alloc)) { fUsedSize += alloc->fSize; return true; } return false; } // need to allocate a new subheap SkAutoTDelete<GrVkSubHeap>& subHeap = fSubHeaps.push_back(); subHeap.reset(new GrVkSubHeap(fGpu, memoryTypeIndex, fSubHeapSize, alignment)); // try to recover from failed allocation by only allocating what we need if (subHeap->size() == 0) { VkDeviceSize alignedSize = align_size(size, alignment); subHeap.reset(new GrVkSubHeap(fGpu, memoryTypeIndex, alignedSize, alignment)); if (subHeap->size() == 0) { return false; } } fAllocSize += fSubHeapSize; if (subHeap->alloc(size, alloc)) { fUsedSize += alloc->fSize; return true; } return false; }