uint32_t mem_ut(void) { #define BLOCK_SIZE MROUND(10) #define BLOCK_COUNT 10 uint8_t MALIGN(4) pool[BLOCK_COUNT][BLOCK_SIZE]; void *mem_free; void *mem_used; uint16_t mem_free_count; void *mem; mem_init(pool, BLOCK_SIZE, BLOCK_COUNT, &mem_free); mem_free_count = mem_free_count_get(mem_free); if (mem_free_count != BLOCK_COUNT) { return 1; } mem_used = 0; while (mem_free_count--) { uint16_t mem_free_count_current; mem = mem_acquire(&mem_free); mem_free_count_current = mem_free_count_get(mem_free); if (mem_free_count != mem_free_count_current) { return 2; } memcpy(mem, &mem_used, sizeof(mem)); mem_used = mem; } mem = mem_acquire(&mem_free); if (mem) { return 3; } while (++mem_free_count < BLOCK_COUNT) { uint16_t mem_free_count_current; mem = mem_used; memcpy(&mem_used, mem, sizeof(void *)); mem_release(mem, &mem_free); mem_free_count_current = mem_free_count_get(mem_free); if ((mem_free_count + 1) != mem_free_count_current) { return 4; } } if (mem != mem_free) { return 5; } if (mem_free_count_get(mem_free) != BLOCK_COUNT) { return 6; } return 0; }
MEM_HANDLE_T egl_server_platform_create_pixmap_info(uint32_t pixmap) { VC_IMAGE_T *vcimage = (VC_IMAGE_T *)pixmap; KHRN_IMAGE_FORMAT_T format = 0; MEM_HANDLE_T data_handle; vcos_assert(pixmap); switch (vcimage->type) { case VC_IMAGE_TF_RGBA32: format = ABGR_8888_TF; break; case VC_IMAGE_TF_RGBX32: format = XBGR_8888_TF; break; case VC_IMAGE_TF_RGB565: format = RGB_565_TF; break; case VC_IMAGE_TF_RGBA5551: format = RGBA_5551_TF; break; case VC_IMAGE_TF_RGBA16: format = RGBA_4444_TF; break; #ifdef __VIDEOCORE4__ case VC_IMAGE_RGBA32: format = ABGR_8888_RSO; break; case VC_IMAGE_RGB565: format = RGB_565_RSO; break; #endif default: UNREACHABLE(); } if (vcimage->mem_handle != MEM_INVALID_HANDLE) { data_handle = vcimage->mem_handle; mem_acquire(data_handle); } else data_handle = mem_wrap(vcimage->image_data, vcimage->size, 64, MEM_FLAG_NONE, "egl_server_platform_create_pixmap_info"); if (data_handle == MEM_INVALID_HANDLE) { return MEM_INVALID_HANDLE; } MEM_HANDLE_T handle = khrn_image_create_from_storage(format, vcimage->width, vcimage->height, vcimage->pitch, MEM_INVALID_HANDLE, data_handle, 0, (KHRN_IMAGE_CREATE_FLAG_T)(IMAGE_CREATE_FLAG_TEXTURE | IMAGE_CREATE_FLAG_RENDER_TARGET)); /* todo: are these flags right? */ mem_release(data_handle); return handle; }
bool khrn_fmem_interlock(KHRN_FMEM_T *fmem, MEM_HANDLE_T handle, uint32_t offset) { KHRN_FMEM_TWEAK_T *tw; tw = tweak_next(fmem, &fmem->interlock); if (!tw) return false; tw->interlock.mh_handle = handle; tw->interlock.offset = offset; mem_acquire(handle); return true; }
EGL_DISP_HANDLE_T egl_disp_alloc( uint64_t pid, uint32_t sem, uint32_t n, const MEM_HANDLE_T *images) { #ifdef BRCM_V3D_OPT return EGL_DISP_HANDLE_INVALID; #endif EGL_DISP_HANDLE_T disp_handle; DISP_T *disp; uint32_t i; vcos_assert(n <= IMAGES_N_MAX); disp_handle = alloc_disp_handle(); if (disp_handle == EGL_DISP_HANDLE_INVALID) { return EGL_DISP_HANDLE_INVALID; } disp = disp_from_handle(disp_handle); disp->in_use.pid = pid; disp->in_use.sem = sem; disp->in_use.n = n; for (i = 0; i != n; ++i) { KHRN_IMAGE_T *image = (KHRN_IMAGE_T *)mem_lock(images[i]); vcos_assert(image->flags & IMAGE_FLAG_DISPLAY); if (n != 1) { image->interlock.disp_image_handle = egl_disp_image_handle(disp_handle, i); } mem_unlock(images[i]); mem_acquire(images[i]); disp->in_use.images[i] = images[i]; } disp->in_use.last_win = EGL_PLATFORM_WIN_NONE; /* we need to make it look like there's something on the display (and it's * been there long enough -- swap interval 0), but there's nothing queued up * (next_pos(on) == post). we also want to make sure the next image to be * displayed is 0 */ disp->in_use.post = next_power_of_2(n); disp->in_use.on = n - 1; disp->in_use.asyncs = -1; /* we don't want an async when the fake image "comes off the display" */ disp->in_use.want = true; disp->in_use.want_us = 0; /* todo: will probably get spurious khrn_hw_kick() on first display. care? */ disp->in_use.finish = false; disp->in_use.slots[n - 1].swap_interval = 0; return disp_handle; }