Beispiel #1
0
void *quantizate(float *x, size_t *n, const float factor, int *nbbits)
{
    size_t i;
    int min, max;
    void *res;
    int *q;
    float real_factor = factor;

    q = malloc(*n * sizeof(int));
    min = max = 0;
    for (i = 0; i < *n; i++)
    {
        if ((i < *n / 2 && is_pow2(i)) || (i > *n / 2 && is_pow2(i - *n / 2)))
            real_factor *= 1.0f;
        if (i == *n / 2)
            real_factor = factor;
        /*q[i] = sign(x[i]) * sqrtf(abs(x[i]) / real_factor);*/
        q[i] = sign(x[i]) * powf(abs(x[i]) / real_factor, 3.0f / 4.0f);
        /*q[i] = sign(x[i]) * floorf(abs(x[i] / factor));*/
        if (q[i] > max)
            max = q[i];
        else if (q[i] < min)
            min = q[i];
    }
    min = abs(min);
    max = max > min ? max : min;
    min = nb_bits(max);
    res = encode(q, *n, min, n);
    *nbbits = min;
    free(q);
    return res;
}
Beispiel #2
0
static void texture_set_data(texture_t *tex,
        const uint8_t *data, int w, int h, int bpp)
{
    uint8_t *buff0 = NULL;
    int data_type = GL_UNSIGNED_BYTE;

    if (!is_pow2(w) || !is_pow2(h)) {
        buff0 = calloc(bpp, tex->tex_w * tex->tex_h);
        blit(data, w, h, bpp, buff0, tex->tex_w, tex->tex_h);
        data = buff0;
    }

    GL(glGenTextures(1, &tex->tex));
    GL(glActiveTexture(GL_TEXTURE0));
    GL(glBindTexture(GL_TEXTURE_2D, tex->tex));
    GL(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR));
    GL(glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
            (tex->flags & TF_MIPMAP)? GL_LINEAR_MIPMAP_NEAREST : GL_LINEAR));
    GL(glTexImage2D(GL_TEXTURE_2D, 0, tex->format, tex->tex_w, tex->tex_h,
                0, tex->format, data_type, data));
    free(buff0);

    if (tex->flags & TF_MIPMAP)
        GL(glGenerateMipmap(GL_TEXTURE_2D));
}
Beispiel #3
0
float *dequantizate(uint8_t *x, size_t *n, const float factor, int nbbits)
{
    size_t i;
    size_t nb_elmts = (((*n - 1) * 8) / nbbits);
    float *res = malloc(nb_elmts * sizeof(float));
    int nb;
    int offset;
    float real_factor = factor;

    offset = 0;
    for (i = 0; i < nb_elmts; i++)
    {
        if ((i < nb_elmts / 2 && is_pow2(i))
                || (i > nb_elmts / 2 && is_pow2(i - nb_elmts / 2)))
            real_factor *= 1.0f;
        if (i == nb_elmts / 2)
            real_factor = factor;
        nb = next_nb(&x, nbbits, &offset);
        if (nb == 0)
            res[i] = 0.0f;
        else
            /*res[i] = sign(nb) * powf(abs(nb), 2) * real_factor;*/
            res[i] = sign(nb) * powf(abs(nb), 4.0f / 3.0f) * real_factor;
        /*res[i] = sign(nb) * (abs(nb) + 0.5f) * factor;*/
    }
    *n = nb_elmts;
    return res;
}
Beispiel #4
0
texture_t gs_create_texture(uint32_t width, uint32_t height,
		enum gs_color_format color_format, uint32_t levels,
		const void **data, uint32_t flags)
{
	graphics_t graphics = thread_graphics;
	bool pow2tex = is_pow2(width) && is_pow2(height);
	bool uses_mipmaps = (flags & GS_BUILDMIPMAPS || levels != 1);

	if (uses_mipmaps && !pow2tex) {
		blog(LOG_WARNING, "Cannot use mipmaps with a "
		                  "non-power-of-two texture.  Disabling "
		                  "mipmaps for this texture.");

		uses_mipmaps = false;
		flags &= ~GS_BUILDMIPMAPS;
		levels = 1;
	}

	if (uses_mipmaps && flags & GS_RENDERTARGET) {
		blog(LOG_WARNING, "Cannot use mipmaps with render targets.  "
		                  "Disabling mipmaps for this texture.");
		flags &= ~GS_BUILDMIPMAPS;
		levels = 1;
	}

	return graphics->exports.device_create_texture(graphics->device,
			width, height, color_format, levels, data, flags);
}
Beispiel #5
0
static int larger_pow2(int n)
{
	if (is_pow2(n))
		return n;

	while(!is_pow2(n))
		n= n&(n-1);

	return n*2;
}
Beispiel #6
0
void test_math(void) {
	test_floor_log2();
	test_ceil_log2();
	test_exact_log2();
	test_hyperfloor();

	assert(is_pow2(1));
	assert(is_pow2(4096));
	assert(!is_pow2(7));
	assert(!is_pow2(9999));
}
Beispiel #7
0
static int smaller_pow2(int n)
{
	while (!is_pow2(n))
		n= n&(n-1);

	return n;
}
Beispiel #8
0
static void split_width(int x, int n, int *splitx, int *nx)
{
	int a, newnx, waste;

	/* if already power of two just use it */
	if(is_pow2(x)) {
		splitx[0]= x;
		(*nx)++;
		return;
	}

	if(n == 1) {
		/* last part, we have to go larger */
		splitx[0]= larger_pow2(x);
		(*nx)++;
	}
	else {
		/* two or more parts to go, use smaller part */
		splitx[0]= smaller_pow2(x);
		newnx= ++(*nx);
		split_width(x-splitx[0], n-1, splitx+1, &newnx);

		for(waste=0, a=0; a<n; a++)
			waste += splitx[a];

		/* if we waste more space or use the same amount,
		 * revert deeper splits and just use larger */
		if(waste >= larger_pow2(x)) {
			splitx[0]= larger_pow2(x);
			memset(splitx+1, 0, sizeof(int)*(n-1));
		}
		else
			*nx= newnx;
	}
}
Beispiel #9
0
int BL_Texture::GetPow2(int n)
{
    if(!is_pow2(n))
        n = smaller_pow2(n);

    return n;
}
Beispiel #10
0
static void
resize(struct hmap *hmap, size_t new_mask, const char *where)
{
    struct hmap tmp;
    size_t i;

    ovs_assert(is_pow2(new_mask + 1));

    hmap_init(&tmp);
    if (new_mask) {
        tmp.buckets = xmalloc(sizeof *tmp.buckets * (new_mask + 1));
        tmp.mask = new_mask;
        for (i = 0; i <= tmp.mask; i++) {
            tmp.buckets[i] = NULL;
        }
    }
    for (i = 0; i <= hmap->mask; i++) {
        struct hmap_node *node, *next;
        int count = 0;
        for (node = hmap->buckets[i]; node; node = next) {
            next = node->next;
            hmap_insert_fast(&tmp, node, node->hash);
            count++;
        }
        if (count > 5) {
            static struct vlog_rate_limit rl = VLOG_RATE_LIMIT_INIT(10, 10);
            COVERAGE_INC(hmap_pathological);
            VLOG_DBG_RL(&rl, "%s: %d nodes in bucket (%"PRIuSIZE" nodes, %"PRIuSIZE" buckets)",
                        where, count, hmap->n, hmap->mask + 1);
        }
    }
    hmap_swap(hmap, &tmp);
    hmap_destroy(&tmp);
}
Beispiel #11
0
void vchiq_init_state(VCHIQ_STATE_T *state, VCHIQ_CHANNEL_T *local, VCHIQ_CHANNEL_T *remote)
{
   VCOS_THREAD_ATTR_T attrs;
   char threadname[8];
   static int id = 0;

   vcos_assert(is_pow2(VCHIQ_CHANNEL_SIZE));

   vcos_assert(is_pow2(VCHIQ_NUM_CURRENT_BULKS));
   vcos_assert(is_pow2(VCHIQ_NUM_SERVICE_BULKS));

   vcos_assert(sizeof(VCHIQ_HEADER_T) == 8);    /* we require this for consistency between endpoints */

   memset(state, 0, sizeof(VCHIQ_STATE_T));
   state->id = id++;

   /*
      initialize events and mutex
   */

   vcos_event_create(&state->connect, "vchiq");
   vcos_mutex_create(&state->mutex, "vchiq");

   /*
      initialize channel pointers
   */

   state->local  = local;
   state->remote = remote;
   vchiq_init_channel(local);

   /*
      bring up slot handler thread
   */

   vcos_thread_attr_init(&attrs);
   vcos_thread_attr_setstacksize(&attrs, VCHIQ_SLOT_HANDLER_STACK);
   vcos_thread_attr_setpriority(&attrs, 5); /* FIXME: should not be hardcoded */
   vcos_thread_attr_settimeslice(&attrs, 20); /* FIXME: should not be hardcoded */
   strcpy(threadname, "VCHIQ-0");
   threadname[6] += state->id % 10;
   vcos_thread_create(&state->slot_handler_thread, threadname,
                      &attrs, slot_handler_func, state);

   /* Indicate readiness to the other side */
   local->initialised = 1;
}
Beispiel #12
0
RADCFUNC HRAD3DIMAGE Open_RAD_3D_image( HRAD3D rad_3d,
                                        u32 width,
                                        u32 height,
                                        s32 alpha_pixels,
                                        u32 maximum_texture_size )
{
  if ( ( is_pow2( width ) && is_pow2( height ) ) || ( rad_3d->nonpow2_textures_supported ) )
  {
    return Open_RAD_3D_image_lin( rad_3d, width, height,
        alpha_pixels, maximum_texture_size );
  }
  else
  {
    return Open_RAD_3D_image_pow2( rad_3d, width, height,
        alpha_pixels, maximum_texture_size );
  }
}
Beispiel #13
0
/* Initializes 'q' as an empty byteq that uses the 'size' bytes of 'buffer' to
 * store data.  'size' must be a power of 2.
 *
 * The caller must ensure that 'buffer' remains available to the byteq as long
 * as 'q' is in use. */
void
byteq_init(struct byteq *q, uint8_t *buffer, size_t size)
{
    ovs_assert(is_pow2(size));
    q->buffer = buffer;
    q->size = size;
    q->head = q->tail = 0;
}
Beispiel #14
0
/** Initialize a fixed heap allocator.
 * @param heap		Heap to initialize.
 * @param mem		Memory area to use.
 * @param size		Size of memory area. */
void fixed_heap_init(fixed_heap_t *heap, void *mem, size_t size) {
	assert(size >= (sizeof(fixed_heap_tag_t) + 8));
	assert(is_pow2(size));

	/* Create an initial free segment covering the entire chunk. */
	heap->tags = mem;
	heap->tags->next = NULL;
	heap->tags->data = size;
}
Beispiel #15
0
UniqueRange Allocate(size_t size, size_t alignment)
{
	ENSURE(is_pow2(alignment));
	if(alignment <= (size_t)idxDeleterBits)
		alignment = idxDeleterBits+1;

	const size_t alignedSize = round_up(size, alignment);
	const UniqueRange::pointer p = rtl_AllocateAligned(alignedSize, alignment);
	return RVALUE(UniqueRange(p, size, idxDeleterAligned));
}
Beispiel #16
0
void BL_Texture::InitGLTex(unsigned int *pix,int x,int y,bool mipmap)
{
    if (!is_pow2(x) || !is_pow2(y) ) {
        InitNonPow2Tex(pix, x,y,mipmap);
        return;
    }

    glBindTexture(GL_TEXTURE_2D, mTexture );
    if( mipmap ) {
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
        gluBuild2DMipmaps( GL_TEXTURE_2D, GL_RGBA, x, y, GL_RGBA, GL_UNSIGNED_BYTE, pix );
    }
    else {
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
        glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
        glTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA, x, y, 0, GL_RGBA, GL_UNSIGNED_BYTE, pix );
    }

    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
}
Beispiel #17
0
UniqueRange AllocateAligned(size_t size, size_t alignment)
{
	ENSURE(is_pow2(alignment));
	alignment = std::max(alignment, allocationAlignment);

	const size_t alignedSize = round_up(size, alignment);
	const UniqueRange::pointer p = rtl_AllocateAligned(alignedSize, alignment);

	static volatile IdxDeleter idxDeleterAligned;
	if(idxDeleterAligned == 0)	// (optional optimization)
		RegisterUniqueRangeDeleter(FreeAligned, &idxDeleterAligned);

	return RVALUE(UniqueRange(p, size, idxDeleterAligned));
}
int vchiu_queue_init(VCHIU_QUEUE_T *queue, int size)
{
	WARN_ON(!is_pow2(size));

	queue->size = size;
	queue->read = 0;
	queue->write = 0;

	sema_init(&queue->pop, 0);
	sema_init(&queue->push, 0);

	queue->storage = kzalloc(size * sizeof(VCHIQ_HEADER_T *), GFP_KERNEL);
	if (queue->storage == NULL) {
		vchiu_queue_delete(queue);
		return 0;
	}
	return 1;
}
Beispiel #19
0
int vchiu_queue_init(VCHIU_QUEUE_T *queue, int size)
{
   vcos_assert(is_pow2(size));

   queue->size = size;
   queue->read = 0;
   queue->write = 0;

   vcos_event_create(&queue->pop, "vchiu");
   vcos_event_create(&queue->push, "vchiu");

   queue->storage = vcos_malloc(size * sizeof(VCHIQ_HEADER_T *), VCOS_FUNCTION);
   if (queue->storage == NULL)
   {
      vchiu_queue_delete(queue);
      return 0;
   }
   return 1;
}
Beispiel #20
0
int vchiu_queue_init(struct vchiu_queue *queue, int size)
{
	WARN_ON(!is_pow2(size));

	queue->size = size;
	queue->read = 0;
	queue->write = 0;
	queue->initialized = 1;

	init_completion(&queue->pop);
	init_completion(&queue->push);

	queue->storage = kcalloc(size, sizeof(struct vchiq_header *),
				 GFP_KERNEL);
	if (!queue->storage) {
		vchiu_queue_delete(queue);
		return 0;
	}
	return 1;
}
Beispiel #21
0
/**
 * Build a QHT RESET message.
 *
 * @param slots		amount of slots in the table (power of 2)
 * @param inf_val	infinity value (1)
 *
 * @return a /QHT message with a RESET payload.
 */
pmsg_t *
g2_build_qht_reset(int slots, int inf_val)
{
	g2_tree_t *t;
	char body[6];
	void *p = &body[0];
	pmsg_t *mb;

	g_assert(is_pow2(slots));
	g_assert(1 == inf_val);		/* Only 1-bit patches in G2 */

	p = poke_u8(p, G2_QHT_RESET);
	p = poke_le32(p, slots);
	p = poke_u8(p, inf_val);

	t = g2_tree_alloc(G2_NAME(QHT), body, sizeof body);
	mb = g2_build_pmsg(t);
	g2_tree_free_null(&t);

	return mb;
}
Beispiel #22
0
/* Reallocates 'hindex''s array of buckets to use bitwise mask 'new_mask'. */
static void
hindex_resize(struct hindex *hindex, size_t new_mask)
{
    struct hindex tmp;
    size_t i;

    ovs_assert(is_pow2(new_mask + 1));
    ovs_assert(new_mask != SIZE_MAX);

    hindex_init(&tmp);
    if (new_mask) {
        tmp.buckets = xmalloc(sizeof *tmp.buckets * (new_mask + 1));
        tmp.mask = new_mask;
        for (i = 0; i <= tmp.mask; i++) {
            tmp.buckets[i] = NULL;
        }
    }
    for (i = 0; i <= hindex->mask; i++) {
        struct hindex_node *node, *next;
        int count;

        count = 0;
        for (node = hindex->buckets[i]; node; node = next) {
            struct hindex_node **head = &tmp.buckets[node->hash & tmp.mask];

            next = node->d;
            node->d = *head;
            *head = node;
            count++;
        }
        if (count > 5) {
            COVERAGE_INC(hindex_pathological);
        }
    }
    tmp.n_unique = hindex->n_unique;
    hindex_swap(hindex, &tmp);
    hindex_destroy(&tmp);
}
Beispiel #23
0
void* aligned_malloc(const size_t size, size_t alignment)
{
    // Often, the value of alignment is set to the line size of the L1 data cache as
    // reported by foundation::System::get_l1_data_cache_line_size().  It may happen
    // that this function returns 0 if the CPU cache information cannot be retrieved.
    // For convenience we handle this situation here by using a reasonable alignment
    // value when this happens.
    if (alignment == 0)
        alignment = 16;

    assert(size > 0);
    assert(is_pow2(alignment));

    // Compute the total number of bytes of memory we need to allocate.
    const size_t total_size = size + sizeof(void*) + (alignment - 1);

    // Allocate the memory.
    void** const unaligned_ptr = reinterpret_cast<void**>(malloc(total_size));

    // Handle allocation failures.
    if (!unaligned_ptr)
    {
        log_allocation_failure(total_size);
        return 0;
    }

    // Compute the next aligned address.
    void** const aligned_ptr = align(unaligned_ptr + 1, alignment);

    // Store the address of the unaligned memory block.
    *(aligned_ptr - 1) = unaligned_ptr;

    log_allocation(aligned_ptr, total_size);

    return aligned_ptr;
}
Beispiel #24
0
static int64_t p5ioc2_set_tce_mem(struct io_hub *hub, uint64_t address,
				  uint64_t size)
{
	struct p5ioc2 *ioc = iohub_to_p5ioc2(hub);
	int64_t rc;

	printf("P5IOC2: set_tce_mem(0x%016llx size 0x%llx)\n",
	       address, size);

	/* The address passed must be naturally aligned */
	if (address && !is_pow2(size))
		return OPAL_PARAMETER;
	if (address & (size - 1))
		return OPAL_PARAMETER;

	ioc->tce_base = address;
	ioc->tce_size = size;

	rc = gx_configure_tce_bar(ioc->host_chip, ioc->gx_bus,
				  address, size);
	if (rc)
		return OPAL_INTERNAL_ERROR;
	return OPAL_SUCCESS;
}
Beispiel #25
0
TexHandle tex_create(uint width, uint height) {
	assert(width && height);

	// Validate size
	int max_size = 0;
	glGetIntegerv(GL_MAX_TEXTURE_SIZE, &max_size);
	if(width > max_size || height > max_size)
		LOG_ERROR("Can't create texture so large!");
	if(!(is_pow2(width) && is_pow2(height)))
		LOG_ERROR("Texture dimensions must be a power of 2");

	// Prep pixel data
	void* data = MEM_ALLOC(4 * width * height);
	memset(data, 0, 4 * width * height);
	uint gl_id = _make_gl_texture(data, width, height);
	MEM_FREE(data);

	// Fill texture struct
	Texture new_tex = {
		.gl_id = gl_id,
		.file = NULL,
		.retain_count = 1,
		.active = true,
		.scale = 1.0f,
        .width = width,
        .height = height
	};

	darray_append(&textures, &new_tex);

	return textures.size - 1;
}

TexHandle tex_load(const char* filename) {
	return tex_load_filter(filename, NULL);
}

TexHandle tex_load_filter(const char* filename, TexFilter filter) {
	assert(filename);

	Texture* tex = DARRAY_DATA_PTR(textures, Texture);

	// Look if texture is already loaded
	for(uint i = 0; i < textures.size; ++i) {
		if(tex[i].active) {
			if(tex[i].file && strcmp(tex[i].file, filename) == 0) {
				tex[i].retain_count++;
				return i;
			}
		}
	}

	LOG_INFO("Loading texture (with filtering) from file %s", filename);

	Texture new_tex;

    PixelFormat fmt;
	void* data = image_load(filename, &new_tex.width, &new_tex.height, &fmt);

	if(filter)
		(*filter)((Color*)data, new_tex.width, new_tex.height);

    uint gl_id = _make_gl_texture(data, new_tex.width, new_tex.height);

	new_tex.gl_id = gl_id;
	new_tex.file = strclone(filename);
	new_tex.retain_count = 1;
	new_tex.active = true;
	new_tex.scale = 1.0f;

	darray_append(&textures, &new_tex);

	return textures.size-1;
}
Beispiel #26
0
static int smaller_pow2(int num) {
    while (!is_pow2(num))
        num= num&(num-1);
    return num;
}
Beispiel #27
0
bool BL_Texture::InitCubeMap(int unit,  EnvMap *cubemap)
{
    if (!GLEW_ARB_texture_cube_map)
    {
        spit("cubemaps not supported");
        mOk = false;
        return mOk;
    }
    else if (!cubemap || cubemap->ima->ok==0)
    {
        mOk = false;
        return mOk;
    }

    ImBuf *ibuf= BKE_image_get_ibuf(cubemap->ima, NULL);
    if (ibuf==0)
    {
        cubemap->ima->ok = 0;
        mOk = false;
        return mOk;
    }

    mNeedsDeleted =	1;
    mType = GL_TEXTURE_CUBE_MAP_ARB;
    mTexture = 0;
    mUnit = unit;

    ActivateUnit(mUnit);

    BL_TextureMap::iterator mapLook = g_textureManager.find(cubemap->ima->id.name);
    if (mapLook != g_textureManager.end())
    {
        if (mapLook->second.gl_texture != 0 && mapLook->second.ref_buffer == cubemap->ima)
        {
            mTexture = mapLook->second.gl_texture;
            glBindTexture(GL_TEXTURE_CUBE_MAP_ARB, mTexture);
            mOk = IsValid();
            return mOk;
        }
    }


    glGenTextures(1, (GLuint*)&mTexture);
    glBindTexture(GL_TEXTURE_CUBE_MAP_ARB, mTexture);


    // track created units
    BL_TextureObject obj;
    obj.gl_texture = mTexture;
    obj.ref_buffer = cubemap->ima;
    g_textureManager.insert(std::pair<char*, BL_TextureObject>((char*)cubemap->ima->id.name, obj));


    bool needs_split = false;
    if (!cubemap->cube[0])
    {
        needs_split = true;
        spit ("Re-Generating texture buffer");
    }

    if (needs_split)
        my_envmap_split_ima(cubemap, ibuf);


    if (!is_pow2(cubemap->cube[0]->x) || !is_pow2(cubemap->cube[0]->y))
    {
        spit("invalid envmap size please render with CubeRes @ power of two");

        my_free_envmapdata(cubemap);
        mOk = false;
        return mOk;
    }


#define SetCubeMapFace(face, num)   \
	glTexImage2D(face, 0,GL_RGBA,	\
	cubemap->cube[num]->x,          \
	cubemap->cube[num]->y,          \
	0, GL_RGBA, GL_UNSIGNED_BYTE,   \
	cubemap->cube[num]->rect)

    SetCubeMapFace(GL_TEXTURE_CUBE_MAP_POSITIVE_X_ARB, 5);
    SetCubeMapFace(GL_TEXTURE_CUBE_MAP_NEGATIVE_X_ARB, 3);
    SetCubeMapFace(GL_TEXTURE_CUBE_MAP_POSITIVE_Y_ARB, 0);
    SetCubeMapFace(GL_TEXTURE_CUBE_MAP_NEGATIVE_Y_ARB, 1);
    SetCubeMapFace(GL_TEXTURE_CUBE_MAP_POSITIVE_Z_ARB, 2);
    SetCubeMapFace(GL_TEXTURE_CUBE_MAP_NEGATIVE_Z_ARB, 4);

    glTexParameteri( GL_TEXTURE_CUBE_MAP_ARB, GL_TEXTURE_MIN_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_CUBE_MAP_ARB, GL_TEXTURE_MAG_FILTER, GL_LINEAR );
    glTexParameteri( GL_TEXTURE_CUBE_MAP_ARB, GL_TEXTURE_WRAP_S,	 GL_CLAMP_TO_EDGE );
    glTexParameteri( GL_TEXTURE_CUBE_MAP_ARB, GL_TEXTURE_WRAP_T,	 GL_CLAMP_TO_EDGE );
    if(GLEW_VERSION_1_2)
        glTexParameteri( GL_TEXTURE_CUBE_MAP_ARB, GL_TEXTURE_WRAP_R,	 GL_CLAMP_TO_EDGE );

    if (needs_split)
        my_free_envmapdata(cubemap);



    glDisable(GL_TEXTURE_CUBE_MAP_ARB);
    ActivateUnit(0);

    mOk = IsValid();
    return mOk;
}
Beispiel #28
0
/* Returns true if 'protocol' is a single OFPUTIL_P_* value, false
 * otherwise. */
bool
ofputil_protocol_is_valid(enum ofputil_protocol protocol)
{
    return protocol & OFPUTIL_P_ANY && is_pow2(protocol);
}
Beispiel #29
0
int buf_ctor(struct buf_s *buf, size_t bsiz, size_t rblk, size_t wblk, int rline, int wline, size_t hpage, size_t ioar, size_t ioaw)
{
	int ret = -1;
	size_t adj, page, idx, rblki, wblki, bsiza, csiza;

	if (!buf) {
		fputs("buf: no buf ?\n", stderr);
		return -1;
	}

	if (bsiz < 2*rblk || bsiz < 2*wblk) {
		fputs("buf: 'buffer size' must be at least 2*max('read block, 'write block'),\n"
		      "     to avoid corner case starvations.\n", stderr);
		return -1;
	}
	memset(buf, 0, sizeof *buf);

#ifndef h_mingw
	page = sysconf(_SC_PAGESIZE);
	if (page == hpage) {
		hpage = 0;
	}
	page = hpage ? hpage : page;
	adj = MAX(page, SHMLBA);
#else
	hpage = 0;
	adj = page = 4096;
#endif

	bsiza = ALIGN(bsiz, adj);
	if (!(idx = is_pow2(bsiza))) {
		fprintf(stderr, "buf: 'aligned buffer size' must be power of 2, but is: 0x%zX\n", bsiza);
		goto out;
	}
	buf->mask = (((size_t)1 << idx) - 1);
	rblki = ALIGN(rblk, ioar);
	wblki = ALIGN(wblk, ioaw);
	csiza = ALIGN(rblki + wblki, adj);
	buf->size = bsiza;

	preset_shm(buf);
	if (setup_shm(buf, bsiza, csiza, hpage) < 0) {
		fputs("buf: falling back to regular malloc()\n", stderr);
		ret = 1;
		detach_shm(buf);
		rm_shm(buf);
		preset_mal(buf);
		if (setup_mal(buf, bsiza, csiza, adj) < 0) {
			detach_mal(buf);
			ret = -1;
			goto out;
		}
	} else
		ret = 0;

	buf->rchunk = buf->chk;
	buf->wchunk = buf->chk + rblki;

	buf->flags |= hpage && buf->mapW ? M_HUGE : 0;
	buf->flags |= rline ? M_LINER : 0;
	buf->flags |= wline ? M_LINEW : 0;
//	buf->page = page;
	buf->ioar = ioar;
	buf->ioaw = ioaw;
	buf->rblk = rblk;
	buf->wblk = wblk;
	buf->crcw = crc_beg();
	buf->crcr = buf->crcw;
#if 0
	if (rblk < wblk && rline && !wline) {
		fputs("buf: 'read block' must be greater or equal to 'write block',\n"
		      "     if the left side is in the line mode,\n"
		      "     and the right side is in the reblocking mode.\n", stderr);
		goto out;
	}
#endif

	DEB("\nbuf map: C:%p, B:%p, B+S:%p, W:%p\n", buf->mapC, buf->mapB, buf->mapB + buf->size, buf->mapW);
	DEB("buf buf: C:%p, B:%p\n", buf->chk, buf->buf);
out:
	if (ret < 0)
		buf_dtor(buf);
	fputc('\n', stderr);
	return ret;
}
Beispiel #30
0
// read full kernel into obuf[], gzip-decompress into ibuf[],
// return decompressed size
int PackVmlinuzI386::decompressKernel()
{
    // read whole kernel image
    obuf.alloc(file_size);
    fi->seek(0, SEEK_SET);
    fi->readx(obuf, file_size);

    {
    const upx_byte *base = NULL;
    unsigned relocated = 0;

    // See startup_32: in linux/arch/i386/boot/compressed/head.S
    const upx_byte *p = &obuf[setup_size];
    unsigned cpa_0 = 0;
    unsigned cpa_1 = 0;
    int j;
    if (0x205<=h.version) {
        cpa_0 = h.kernel_alignment;
        cpa_1 = 0u - cpa_0;
    } else
    for ((p = &obuf[setup_size]), (j= 0); j < 0x200; ++j, ++p) {
        if (0==memcmp("\x89\xeb\x81\xc3", p, 4)
        &&  0==memcmp("\x81\xe3",      8+ p, 2)) {
            // movl %ebp,%ebx
            // addl $imm.w,%ebx
            // andl $imm.w,%ebx
            cpa_0 = 1+ get_te32( 4+ p);
            cpa_1 =    get_te32(10+ p);
            break;
        }
    }
    for ((p = &obuf[setup_size]), (j= 0); j < 0x200; ++j, ++p) {
        if (0==memcmp("\x8d\x83",    p, 2)  // leal d32(%ebx),%eax
        &&  0==memcmp("\xff\xe0", 6+ p, 2)  // jmp *%eax
        ) {
            relocated = get_te32(2+ p);
        }
        if (0==memcmp("\xE8\x00\x00\x00\x00\x5D", p, 6)) {
            // "call 1f; 1f: pop %ebp"  determines actual execution address.
            // linux-2.6.21 (spring 2007) and later; upx stub needs work
            // unless LOAD_PHYSICAL_ADDR is known.
            // Allowed code is:  linux-2.6.23/arch/x86/head_32.S  2008-01-01
            //      call 1f
            //  1:  popl %ebp
            //      subl $1b, %ebp  # 32-bit immediate
            //      movl $LOAD_PHYSICAL_ADDR, %ebx
            //
            if (0==memcmp("\x81\xed", 6+  p, 2)      // subl $imm.w,%ebp
            &&  0==memcmp("\xbb",     12+ p, 1) ) {  // movl $imm.w,%ebx
                physical_start = get_te32(13+ p);
            } else
            if (0==memcmp("\x81\xed", 6+  p, 2)  // subl $imm.w,%ebp
            &&  is_pow2(cpa_0) && (0u-cpa_0)==cpa_1) {
                base = (5+ p) - get_te32(8+ p);
                config_physical_align = cpa_0;
            }
            else {
                throwCantPack("Unrecognized relocatable kernel");
            }
        }
        // Find "ljmp $__BOOT_CS,$__PHYSICAL_START" if any.
        if (0==memcmp("\xEA\x00\x00", p, 3) && 0==(0xf & p[3]) && 0==p[4]) {
            /* whole megabyte < 16 MiB */
            physical_start = get_te32(1+ p);
            break;
        }
    }
    if (base && relocated) {
        p = base + relocated;
        for (j = 0; j < 0x200; ++j, ++p) {
            if (0==memcmp("\x01\x9c\x0b", p, 3)  // addl %ebx,d32(%ebx,%ecx)
            ) {
                page_offset = 0u - get_te32(3+ p);
            }
            if (0==memcmp("\x89\xeb",    p, 2)  // movl %ebp,%ebx
            &&  0==memcmp("\x81\xeb", 2+ p, 2)  // subl $imm32,%ebx
            ) {
                physical_start = get_te32(4+ p);
            }
        }
    }
    }

    checkAlreadyPacked(obuf + setup_size, UPX_MIN(file_size - setup_size, (off_t)1024));

    int gzoff = setup_size;
    if (0x208<=h.version) {
        gzoff += h.payload_offset;
    }
    for (; gzoff < file_size; gzoff++)
    {
        // find gzip header (2 bytes magic + 1 byte method "deflated")
        int off = find(obuf + gzoff, file_size - gzoff, "\x1F\x8B\x08", 3);
        if (off < 0)
            break;
        gzoff += off;
        const int gzlen = (h.version < 0x208) ? (file_size - gzoff) : h.payload_length;
        if (gzlen < 256)
            break;
        // check gzip flag byte
        unsigned char flags = obuf[gzoff + 3];
        if ((flags & 0xe0) != 0)        // reserved bits set
            continue;
        //printf("found gzip header at offset %d\n", gzoff);

        // try to decompress
        int klen;
        int fd;
        off_t fd_pos;
        for (;;)
        {
            klen = -1;
            fd = -1;
            fd_pos = -1;
            // open
            fi->seek(gzoff, SEEK_SET);
            fd = dup(fi->getFd());
            if (fd < 0)
                break;
            gzFile zf = gzdopen(fd, "rb");
            if (zf == NULL)
                break;
            // estimate gzip-decompressed kernel size & alloc buffer
            if (ibuf.getSize() == 0)
                ibuf.alloc(gzlen * 3);
            // decompress
            klen = gzread(zf, ibuf, ibuf.getSize());
            fd_pos = lseek(fd, 0, SEEK_CUR);
            gzclose(zf);
            fd = -1;
            if (klen != (int)ibuf.getSize())
                break;
            // realloc and try again
            unsigned s = ibuf.getSize();
            ibuf.dealloc();
            ibuf.alloc(3 * s / 2);
        }
        if (fd >= 0)
            (void) close(fd);
        if (klen <= 0)
            continue;

        if (klen <= gzlen)
            continue;

        if (0x208<=h.version && 0==memcmp("\177ELF", ibuf, 4)) {
            // Full ELF in theory; for now, try to handle as .bin at physical_start.
            // Check for PT_LOAD.p_paddr being ascending and adjacent.
            Elf_LE32_Ehdr const *const ehdr = (Elf_LE32_Ehdr const *)(void const *)ibuf;
            Elf_LE32_Phdr const *phdr = (Elf_LE32_Phdr const *)(ehdr->e_phoff + (char const *)ehdr);
            Elf_LE32_Shdr const *shdr = (Elf_LE32_Shdr const *)(ehdr->e_shoff + (char const *)ehdr);
            unsigned hi_paddr = 0, lo_paddr = 0;
            unsigned delta_off = 0;
            for (unsigned j=0; j < ehdr->e_phnum; ++j, ++phdr) {
                if (phdr->PT_LOAD==phdr->p_type) {
                    unsigned step = (hi_paddr + phdr->p_align - 1) & ~(phdr->p_align - 1);
                    if (0==hi_paddr) { // first PT_LOAD
                        if (physical_start!=phdr->p_paddr) {
                            return 0;
                        }
                        delta_off = phdr->p_paddr - phdr->p_offset;
                        lo_paddr = phdr->p_paddr;
                        hi_paddr = phdr->p_filesz + phdr->p_paddr;
                    }
                    else if (step==phdr->p_paddr
                        && delta_off==(phdr->p_paddr - phdr->p_offset)) {
                        hi_paddr = phdr->p_filesz + phdr->p_paddr;
                    }
                    else {
                        return 0;  // Not equivalent to a .bin.  Too complex for now.
                    }
                }
            }
            // FIXME: ascending order is only a convention; might need sorting.
            for (unsigned j=1; j < ehdr->e_shnum; ++j) {
                if (shdr->SHT_PROGBITS==shdr->sh_type) { // SHT_REL might be intermixed
                    if (shdr->SHF_EXECINSTR & shdr[j].sh_flags) {
                        filter_len += shdr[j].sh_size;  // FIXME: include sh_addralign
                    }
                    else {
                        break;
                    }
                }
            }
            memmove(ibuf, (lo_paddr - delta_off) + ibuf, hi_paddr - lo_paddr);  // FIXME: set_size
            // FIXME: .bss ?  Apparently handled by head.S
        }

        if (opt->force > 0)
            return klen;

        // some checks
        if (fd_pos != file_size)
        {
            //printf("fd_pos: %ld, file_size: %ld\n", (long)fd_pos, (long)file_size);

            // linux-2.6.21.5/arch/i386/boot/compressed/vmlinux.lds
            // puts .data.compressed ahead of .text, .rodata, etc;
            // so piggy.o need not be last in bzImage.  Alas.
            //throwCantPack("trailing bytes after kernel image; use option '-f' to force packing");
        }


        // see /usr/src/linux/arch/i386/kernel/head.S
        // 2.4.x: [cli;] cld; mov $...,%eax
        if (memcmp(ibuf,     "\xFC\xB8", 2) == 0) goto head_ok;
        if (memcmp(ibuf, "\xFA\xFC\xB8", 3) == 0) goto head_ok;
        // 2.6.21.5 CONFIG_PARAVIRT  mov %cs,%eax; test $3,%eax; jne ...;
        if (memcmp(ibuf, "\x8c\xc8\xa9\x03\x00\x00\x00\x0f\x85", 9) == 0) goto head_ok;
        if (memcmp(ibuf, "\x8c\xc8\xa8\x03\x0f\x85", 6) == 0) goto head_ok;
        // 2.6.x: [cli;] cld; lgdt ...
        if (memcmp(ibuf,     "\xFC\x0F\x01", 3) == 0) goto head_ok;
        if (memcmp(ibuf, "\xFA\xFC\x0F\x01", 4) == 0) goto head_ok;
        // 2.6.x+grsecurity+strongswan+openwall+trustix: ljmp $0x10,...
        if (ibuf[0] == 0xEA && memcmp(ibuf+5, "\x10\x00", 2) == 0) goto head_ok;
        // x86_64 2.6.x
        if (0xB8==ibuf[0]  // mov $...,%eax
        &&  0x8E==ibuf[5] && 0xD8==ibuf[6]  // mov %eax,%ds
        &&  0x0F==ibuf[7] && 0x01==ibuf[8] && 020==(070 & ibuf[9]) // lgdtl
        &&  0xB8==ibuf[14]  // mov $...,%eax
        &&  0x0F==ibuf[19] && 0xA2==ibuf[20]  // cpuid
        ) goto head_ok;

        // cmpw   $0x207,0x206(%esi)  Debian vmlinuz-2.6.24-12-generic
        if (0==memcmp("\x66\x81\xbe\x06\x02\x00\x00\x07\x02", ibuf, 9)) goto head_ok;

        // testb  $0x40,0x211(%esi)  Fedora vmlinuz-2.6.25-0.218.rc8.git7.fc9.i686
        if (0==memcmp("\xf6\x86\x11\x02\x00\x00\x40", ibuf, 7)) goto head_ok;

        // rex.W prefix for x86_64
        if (0x48==ibuf[0]) throwCantPack("x86_64 bzImage is not yet supported");

        throwCantPack("unrecognized kernel architecture; use option '-f' to force packing");
    head_ok:

        // FIXME: more checks for special magic bytes in ibuf ???
        // FIXME: more checks for kernel architecture ???

        return klen;
    }

    return 0;
}