示例#1
0
文件: gl_binder.c 项目: Ckef/Groufix
static void* _gfx_gl_binder_init(

		size_t  num,
		size_t  size)
{
	size_t unitSize = sizeof(GFX_Unit) + size;

	/* Allocate */
	void* data = calloc(num, unitSize);
	if(!data)
	{
		/* Out of memory error */
		gfx_errors_push(
			GFX_ERROR_OUT_OF_MEMORY,
			"Internal binder could not be allocated."
		);
		return NULL;
	}

	void* bindings = data;

	/* Iterate and set to empty */
	while(num--)
	{
		GFX_Unit* unit = (GFX_Unit*)bindings;
		unit->counter = GFX_BINDER_COUNTER_EMPTY;

		/* Next unit */
		bindings = GFX_PTR_ADD_BYTES(bindings, unitSize);
	}

	return data;
}
示例#2
0
static void APIENTRY _gfx_gl_error_callback(

		GLenum         source,
		GLenum         type,
		GLuint         id,
		GLenum         severity,
		GLsizei        length,
		const GLchar*  message,
		const void*    userParam)
{
	GFXErrorCode code;
	switch(type)
	{
		/* Ignore group and marker calls */
		case GL_DEBUG_TYPE_MARKER :
		case GL_DEBUG_TYPE_PUSH_GROUP :
		case GL_DEBUG_TYPE_POP_GROUP :
			return;

		/* Unknown errors */
		case GL_DEBUG_TYPE_ERROR :
		case GL_DEBUG_TYPE_OTHER :
			code = GFX_ERROR_UNKNOWN;
			break;

		/* Known errors */
		default :
			code = type;
			break;
	}

	/* Push the error */
	gfx_errors_push(code, message);
}
示例#3
0
文件: mesh.c 项目: Ckef/Groufix
GFXMesh* gfx_mesh_create(void)
{
	/* Allocate mesh */
	GFX_Mesh* mesh = malloc(sizeof(GFX_Mesh));
	if(!mesh)
	{
		/* Out of memory error */
		gfx_errors_push(
			GFX_ERROR_OUT_OF_MEMORY,
			"Mesh could not be allocated."
		);
		return NULL;
	}

	/* Initialize */
	_gfx_lod_map_init(
		(GFX_LodMap*)mesh,
		0,
		sizeof(GFX_SourceData),
		sizeof(GFX_SourceData)
	);

	gfx_vector_init(&mesh->layouts, sizeof(GFXVertexLayout*));
	gfx_vector_init(&mesh->buckets, 1);
	gfx_vector_init(&mesh->buffers, sizeof(GFXSharedBuffer));

	return (GFXMesh*)mesh;
}
示例#4
0
GFXThreadPool* gfx_thread_pool_create(

		GFXThreadPoolInit       init,
		GFXThreadPoolTerminate  terminate,
		int                     suspend)
{
	/* Create a new thread pool */
	GFX_Pool* pool = malloc(sizeof(GFX_Pool));
	if(!pool)
	{
		/* Out of memory error */
		gfx_errors_push(
			GFX_ERROR_OUT_OF_MEMORY,
			"Thread pool could not be allocated."
		);
		return NULL;
	}

	/* Create mutex */
	if(_gfx_platform_mutex_init(&pool->mutex))
	{
		/* Create condition variable */
		if(_gfx_platform_cond_init(&pool->assign))
		{
			if(_gfx_platform_cond_init(&pool->flush))
			{
				/* Initialize */
				pool->status = suspend ?
					GFX_INT_POOL_SUSPENDED :
					GFX_INT_POOL_RESUMED;

				pool->pool.size = 0;
				pool->pool.init = init;
				pool->pool.terminate = terminate;

				gfx_vector_init(&pool->tasks, sizeof(GFX_Task));

				pool->threads = NULL;
				pool->deads = NULL;

				return (GFXThreadPool*)pool;
			}

			_gfx_platform_cond_clear(&pool->assign);
		}

		_gfx_platform_mutex_clear(&pool->mutex);
	}

	/* Nevermind */
	free(pool);

	return NULL;
}
示例#5
0
static int _gfx_x11_load_extensions(

		int*  major,
		int*  minor)
{
	int num = XDefaultScreen(_gfx_x11.display);

	/* Check XRandR version */
	if(
		!XRRQueryVersion(_gfx_x11.display, major, minor) ||
		*major < 1 ||
		(*major == 1 && *minor < 2))
	{
		gfx_errors_push(GFX_ERROR_INCOMPATIBLE_CONTEXT, "RandR 1.2 is not supported.");
		return 0;
	}

	/* Check all vital extensions */
	if(
		!_gfx_x11_is_extension_supported(num, "GLX_ARB_get_proc_address") ||
		!_gfx_x11_is_extension_supported(num, "GLX_ARB_create_context") ||
		!_gfx_x11_is_extension_supported(num, "GLX_ARB_create_context_profile"))
	{
		gfx_errors_push(GFX_ERROR_INCOMPATIBLE_CONTEXT, "Vital GLX extensions are missing.");
		return 0;
	}

	/* Load all functions */
	_gfx_x11.extensions.CreateContextAttribsARB =
		(PFNGLXCREATECONTEXTATTRIBSARBPROC)glXGetProcAddressARB((const GLubyte*)"glXCreateContextAttribsARB");
	_gfx_x11.extensions.SwapIntervalEXT =
		(PFNGLXSWAPINTERVALEXTPROC)glXGetProcAddressARB((const GLubyte*)"glXSwapIntervalEXT");
	_gfx_x11.extensions.EXT_swap_control_tear =
		_gfx_x11_is_extension_supported(num, "GLX_EXT_swap_control_tear") ? 1 : 0;

	/* Check non-vital extensions */
	if(!_gfx_x11_is_extension_supported(num, "GLX_EXT_swap_control"))
		_gfx_x11.extensions.SwapIntervalEXT = NULL;

	return 1;
}
示例#6
0
void _gfx_renderer_poll_errors(void)
{
	GFX_CONT_INIT();

	/* Loop over all errors */
	GLenum err = GFX_REND_GET.GetError();
	while(err != GL_NO_ERROR)
	{
		gfx_errors_push(err, "An OpenGL error occurred.");
		err = GFX_REND_GET.GetError();
	}
}
示例#7
0
文件: mesh.c 项目: Ckef/Groufix
int _gfx_mesh_add_bucket(

		GFXMesh*    mesh,
		GFXBucket*  bucket)
{
	/* See if it already exists */
	GFX_Mesh* internal =
		(GFX_Mesh*)mesh;
	size_t size =
		_gfx_mesh_bucket_size(mesh, UINT_MAX);
	GFX_Bucket* buck =
		_gfx_mesh_find_bucket(internal, bucket, size);

	if(buck == internal->buckets.end)
	{
		/* Insert bucket */
		buck = gfx_vector_insert_range(
			&internal->buckets,
			size,
			NULL,
			internal->buckets.end
		);

		if(buck == internal->buckets.end)
			return 0;

		/* Initialize bucket, reference and source IDs */
		memset(buck, 0, size);

		buck->bucket = bucket;
		buck->ref = 1;
	}
	else
	{
		/* Increase reference counter */
		if(!(buck->ref + 1))
		{
			/* Overflow error */
			gfx_errors_push(
				GFX_ERROR_OVERFLOW,
				"Overflow occurred during Mesh bucket referencing."
			);
			return 0;
		}
		++buck->ref;
	}

	return 1;
}
示例#8
0
文件: lod_map.c 项目: Ckef/Groufix
GFXLodMap* gfx_lod_map_create(

		GFXLodFlags  flags,
		size_t       dataSize,
		size_t       compSize)
{
	/* Allocate new map */
	GFX_LodMap* map = malloc(sizeof(GFX_LodMap));
	if(map) _gfx_lod_map_init(map, flags, dataSize, compSize);

	/* Out of memory error */
	else gfx_errors_push(
		GFX_ERROR_OUT_OF_MEMORY,
		"Lod Map could not be allocated."
	);

	return (GFXLodMap*)map;
}
示例#9
0
GFXSampler* _gfx_sampler_create(

		const GFXSampler* values)
{
	GFX_CONT_INIT(NULL);

	/* Allocate new sampler */
	GFX_Sampler* samp = calloc(1, sizeof(GFX_Sampler));
	if(!samp)
	{
		/* Out of memory error */
		gfx_errors_push(
			GFX_ERROR_OUT_OF_MEMORY,
			"Sampler could not be allocated."
		);
		return NULL;
	}

	if(GFX_REND_GET.intExt[GFX_INT_EXT_SAMPLER_OBJECTS])
	{
		/* Register as object */
		samp->id = _gfx_render_object_register(
			&GFX_CONT_GET.objects,
			samp,
			&_gfx_sampler_obj_funcs
		);

		if(!samp->id.id)
		{
			free(samp);
			return NULL;
		}

		/* Allocate OGL resources */
		GFX_REND_GET.CreateSamplers(1, &samp->handle);
	}

	/* Initialize */
	samp->references = 1;
	_gfx_sampler_set((GFXSampler*)samp, values);

	return (GFXSampler*)samp;
}
示例#10
0
int _gfx_sampler_reference(

		GFXSampler* sampler)
{
	GFX_Sampler* internal = (GFX_Sampler*)sampler;

	if(!(internal->references + 1))
	{
		/* Overflow error */
		gfx_errors_push(
			GFX_ERROR_OVERFLOW,
			"Overflow occurred during Sampler referencing."
		);
		return 0;
	}

	++internal->references;
	return 1;
}
示例#11
0
static int _gfx_x11_error_handler(

		Display*      display,
		XErrorEvent*  evt)
{
	if(_gfx_x11.errors)
	{
		char* text = malloc(GFX_X11_ERROR_LENGTH);
		XGetErrorText(display, evt->error_code, text, GFX_X11_ERROR_LENGTH);

		/* Make sure it's null terminated */
		text[GFX_X11_ERROR_LENGTH - 1] = 0;
		gfx_errors_push(GFX_ERROR_PLATFORM_ERROR, text);

		free(text);
	}

	return 0;
}
示例#12
0
unsigned char gfx_thread_pool_expand(

		GFXThreadPool*  pool,
		unsigned char   size,
		void*           arg)
{
	GFX_Pool* internal = (GFX_Pool*)pool;

	/* Check for overflow */
	if(USHRT_MAX - size < pool->size)
	{
		gfx_errors_push(
			GFX_ERROR_OVERFLOW,
			"Overflow occurred during thread pool expansion."
		);
		return 0;
	}

	/* Allocate new node */
	if(!size) return 0;

	GFX_ThreadList* node = (GFX_ThreadList*)gfx_list_create(
		sizeof(GFX_ThreadList) +
		sizeof(GFX_PlatformThread) * size
	);

	if(!node) return 0;

	node->alive = 1;
	node->pool = internal;
	node->arg = arg;

	/* Initialize all threads */
	unsigned char s;
	for(s = 0; s < size; ++s)
	{
		if(!_gfx_platform_thread_init(
			_gfx_thread_list_get(node, s),
			_gfx_thread_addr,
			node,
			1))
		{
			break;
		}
	}

	node->size = s;
	pool->size += s;

	/* Fail if none managed to initialize */
	if(!s)
	{
		gfx_list_free((GFXList*)node);
		return 0;
	}

	/* Add thread list */
	if(internal->threads) gfx_list_splice_before(
		(GFXList*)node,
		(GFXList*)internal->threads
	);

	internal->threads = node;

	return s;
}