Esempio n. 1
0
void agp_empty_vstore(struct storage_info_t* vs, size_t w, size_t h)
{
	size_t sz = w * h * sizeof(av_pixel);
	vs->vinf.text.s_raw = sz;

/* this is to allow an override of s_fmt and still handle reset */
	if (vs->vinf.text.s_fmt == 0)
		vs->vinf.text.s_fmt = GL_PIXEL_FORMAT;
	if (vs->vinf.text.d_fmt == 0)
		vs->vinf.text.d_fmt = GL_STORE_PIXEL_FORMAT;

	vs->vinf.text.raw = arcan_alloc_mem(
		vs->vinf.text.s_raw,
		ARCAN_MEM_VBUFFER, ARCAN_MEM_BZERO, ARCAN_MEMALIGN_PAGE
	);
	vs->w = w;
	vs->h = h;
	vs->bpp = sizeof(av_pixel);
	vs->txmapped = TXSTATE_TEX2D;

	agp_update_vstore(vs, true);

	arcan_mem_free(vs->vinf.text.raw);
	vs->vinf.text.raw = 0;
	vs->vinf.text.s_raw = 0;
}
Esempio n. 2
0
struct agp_rendertarget* agp_setup_rendertarget(struct storage_info_t* vstore,
	enum rendertarget_mode m)
{
	struct agp_rendertarget* r = arcan_alloc_mem(sizeof(struct agp_rendertarget),
		ARCAN_MEM_VSTRUCT, ARCAN_MEM_BZERO, ARCAN_MEMALIGN_NATURAL);

	r->store = vstore;
	r->mode = m;

	alloc_fbo(r, false);
	return r;
}
Esempio n. 3
0
File: gl21.c Progetto: mewbak/arcan
static void alloc_buffer(struct storage_info_t* s)
{
	if (s->vinf.text.s_raw != s->w * s->h * sizeof(av_pixel)){
		arcan_mem_free(s->vinf.text.raw);
		s->vinf.text.raw = NULL;
	}

	if (!s->vinf.text.raw){
		s->vinf.text.s_raw = s->w * s->h * sizeof(av_pixel);
		s->vinf.text.raw = arcan_alloc_mem(s->vinf.text.s_raw,
			ARCAN_MEM_VBUFFER, ARCAN_MEM_BZERO, ARCAN_MEMALIGN_PAGE);
	}
}
Esempio n. 4
0
File: mem.c Progetto: Gu1/arcan
/*
 * Allocate memory intended for read-only or 
 * exec use (JIT, ...)
 */
void* arcan_alloc_fillmem(const void* data,
	size_t ds,
	enum arcan_memtypes type, 
	enum arcan_memhint hint, 
	enum arcan_memalign align)
{
	void* buf = arcan_alloc_mem(ds, type, hint, align);

	if (!buf)
		return NULL;
	
	memcpy(buf, data, ds);
	return buf;
}
Esempio n. 5
0
struct agp_rendertarget* agp_setup_rendertarget(
	struct storage_info_t* vstore, enum rendertarget_mode m)
{
	struct agp_rendertarget* r = arcan_alloc_mem(sizeof(struct agp_rendertarget),
		ARCAN_MEM_VSTRUCT, ARCAN_MEM_BZERO, ARCAN_MEMALIGN_NATURAL);

	r->store = vstore;
	r->mode = m;
	r->clearcol[3] = 1.0;

/* need this tracking because there's no external memory management for _back */
	r->front_active = true;

	if (m & RENDERTARGET_DOUBLEBUFFER){
		r->store_back = arcan_alloc_mem(sizeof(struct storage_info_t),
			ARCAN_MEM_VSTRUCT, ARCAN_MEM_BZERO, ARCAN_MEMALIGN_NATURAL);
		r->store_back->vinf.text.s_fmt = vstore->vinf.text.s_fmt;
		r->store_back->vinf.text.d_fmt = vstore->vinf.text.d_fmt;
		agp_empty_vstore(r->store_back, vstore->w, vstore->h);
	}

	alloc_fbo(r, false);
	return r;
}
Esempio n. 6
0
struct agp_fenv* agp_alloc_fenv(
	void*(lookup)(void* tag, const char* sym, bool req), void* tag)
{
	struct agp_fenv* fenv = arcan_alloc_mem(
		sizeof(struct agp_fenv),
		ARCAN_MEM_VSTRUCT, ARCAN_MEM_BZERO, ARCAN_MEMALIGN_NATURAL
	);

/* FIXME:
 * need a WRITELOCK flag to the allocation and calls to writelock afterwards */
	agp_glinit_fenv(fenv, lookup ? lookup : lookup_fun, tag);
	if (!agp_env())
		agp_setenv(fenv);

	return fenv;
}
Esempio n. 7
0
void agp_empty_vstore(struct storage_info_t* vs, size_t w, size_t h)
{
	size_t sz = w * h * sizeof(av_pixel);
	vs->vinf.text.s_raw = sz;
	vs->vinf.text.raw = arcan_alloc_mem(
		vs->vinf.text.s_raw,
		ARCAN_MEM_VBUFFER, ARCAN_MEM_BZERO, ARCAN_MEMALIGN_PAGE
	);
	vs->w = w;
	vs->h = h;
	vs->txmapped = TXSTATE_TEX2D;

	agp_update_vstore(vs, true);

	arcan_mem_free(vs->vinf.text.raw);
	vs->vinf.text.raw = 0;
	vs->vinf.text.s_raw = 0;
}
Esempio n. 8
0
static bool alloc_fbo(struct agp_rendertarget* dst, bool retry)
{
	glGenFramebuffers(1, &dst->fbo);

/* need both stencil and depth buffer, but we don't need the data from them */
	glBindFramebuffer(GL_FRAMEBUFFER, dst->fbo);

	if (dst->mode > RENDERTARGET_DEPTH)
	{
		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0,
			GL_TEXTURE_2D, dst->store->vinf.text.glid, 0);

/* need a Z buffer in the offscreen rendering but don't want
 * bo store it, so setup a renderbuffer */
		if (dst->mode > RENDERTARGET_COLOR) {
			glGenRenderbuffers(1, &dst->depth);

/* could use GL_DEPTH_COMPONENT only if we'd know that there
 * wouldn't be any clipping in the active rendertarget */
			if (!retry){
				glBindRenderbuffer(GL_RENDERBUFFER, dst->depth);
				glRenderbufferStorage(GL_RENDERBUFFER, GL_DEPTH24_STENCIL8,
					dst->store->w, dst->store->h);

				glFramebufferRenderbuffer(GL_FRAMEBUFFER, GL_DEPTH_STENCIL_ATTACHMENT,
					GL_RENDERBUFFER, dst->depth);
			}
		}
	}
	else {
/* DEPTH buffer only (shadowmapping, ...) convert the storage to
 * contain a depth texture */
		size_t w = dst->store->w;
		size_t h = dst->store->h;

		agp_drop_vstore(dst->store);

		dst->store = arcan_alloc_mem(sizeof(struct storage_info_t),
			ARCAN_MEM_VSTRUCT, 0, ARCAN_MEMALIGN_NATURAL);

		struct storage_info_t* store = dst->store;

		memset(store, '\0', sizeof(struct storage_info_t));

		store->txmapped   = TXSTATE_DEPTH;
		store->txu        = ARCAN_VTEX_CLAMP;
		store->txv        = ARCAN_VTEX_CLAMP;
		store->scale      = ARCAN_VIMAGE_NOPOW2;
		store->imageproc  = IMAGEPROC_NORMAL;
		store->filtermode = ARCAN_VFILTER_NONE;
		store->refcount   = 1;
		store->w = w;
		store->h = h;

/* generate ID etc. special path for TXSTATE_DEPTH */
		agp_update_vstore(store, true);

		glDrawBuffer(GL_NONE);
		glReadBuffer(GL_NONE);

		glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT,
			GL_TEXTURE_2D, store->vinf.text.glid, 0);
	}

/* basic error handling / status checking
 * may be possible that we should cache this in the
 * rendertarget and only call when / if something changes as
 * it's not certain that drivers won't stall the pipeline on this */
	GLenum status = glCheckFramebufferStatus(GL_FRAMEBUFFER);
	if (status != GL_FRAMEBUFFER_COMPLETE){
		arcan_warning("FBO support broken, couldn't create basic FBO:\n");
		switch(status){
		case GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT:
			if (!retry){
				arcan_warning("\t Incomplete Attachment, attempting "
					"simple framebuffer, this will likely break 3D and complex"
					"clipping operations.\n");
				return alloc_fbo(dst, true);
			}
			else
				arcan_warning("\t Simple attachement broke as well "
					"likely driver issue.\n");
		break;

#ifdef GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS
		case GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS:
			arcan_warning("\t Not all attached buffers have "
				"the same dimensions.\n");
		break;
#endif

		case GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT:
			arcan_warning("\t One or several FBO attachment points are missing.\n");
		break;

		case GL_FRAMEBUFFER_UNSUPPORTED:
			arcan_warning("\t Request formats combination unsupported.\n");
		break;
		}

		if (dst->fbo != GL_NONE)
			glDeleteFramebuffers(1,&dst->fbo);
		if (dst->depth != GL_NONE)
			glDeleteRenderbuffers(1,&dst->depth);

		dst->fbo = dst->depth = GL_NONE;
		return false;
	}

	glBindFramebuffer(GL_FRAMEBUFFER, 0);
	return true;
}