Example #1
0
static void ep_parse_technique(struct effect_parser *ep)
{
	struct ep_technique ept;
	ep_technique_init(&ept);

	if (cf_next_name(&ep->cfp, &ept.name, "name", ";") != PARSE_SUCCESS)
		goto error;

	if (!cf_next_valid_token(&ep->cfp))
		return;

	if (!cf_token_is(&ep->cfp, "{")) {
		if (!cf_go_to_token(&ep->cfp, ";", NULL)) {
			cf_adderror_expecting(&ep->cfp, ";");
			return;
		}

		cf_adderror_expecting(&ep->cfp, "{");
		goto error;
	}
	if (!cf_next_valid_token(&ep->cfp))
		goto error;

	while (!cf_token_is(&ep->cfp, "}")) {
		struct ep_pass pass;
		ep_pass_init(&pass);

		switch (ep_parse_pass(ep, &pass)) {
		case PARSE_UNEXPECTED_CONTINUE:
			ep_pass_free(&pass);
			if (!cf_go_to_token(&ep->cfp, "}", NULL))
				goto error;
			continue;
		case PARSE_EOF:
			ep_pass_free(&pass);
			goto error;
		}

		da_push_back(ept.passes, &pass);

		if (!cf_next_valid_token(&ep->cfp))
			goto error;
	}

	/* pass the current token (which is '}') if we reached here */
	cf_next_token(&ep->cfp);

	da_push_back(ep->techniques, &ept);
	return;

error:
	cf_next_token(&ep->cfp);
	ep_technique_free(&ept);
}
Example #2
0
static inline int ep_parse_param_assign_intfloat(struct effect_parser *ep,
		struct ep_param *param, bool is_float)
{
	int code;
	bool is_negative = false;

	if (!cf_next_valid_token(&ep->cfp))
		return PARSE_EOF;

	if (cf_token_is(&ep->cfp, "-")) {
		is_negative = true;

		if (!cf_next_token(&ep->cfp))
			return PARSE_EOF;
	}

	code = cf_token_is_type(&ep->cfp, CFTOKEN_NUM, "numeric value", ";");
	if (code != PARSE_SUCCESS)
		return code;

	if (is_float) {
		float f = (float)os_strtod(ep->cfp.cur_token->str.array);
		if (is_negative) f = -f;
		da_push_back_array(param->default_val, &f, sizeof(float));
	} else {
		long l = strtol(ep->cfp.cur_token->str.array, NULL, 10);
		if (is_negative) l = -l;
		da_push_back_array(param->default_val, &l, sizeof(long));
	}

	return PARSE_SUCCESS;
}
Example #3
0
static int ep_parse_pass(struct effect_parser *ep, struct ep_pass *pass)
{
	struct cf_token peek;

	if (!cf_token_is(&ep->cfp, "pass"))
		return PARSE_UNEXPECTED_CONTINUE;

	if (!cf_next_valid_token(&ep->cfp)) return PARSE_EOF;

	if (!cf_token_is(&ep->cfp, "{")) {
		pass->name = bstrdup_n(ep->cfp.cur_token->str.array,
					ep->cfp.cur_token->str.len);
		if (!cf_next_valid_token(&ep->cfp)) return PARSE_EOF;
	}

	if (!cf_peek_valid_token(&ep->cfp, &peek)) return PARSE_EOF;

	while (strref_cmp(&peek.str, "}") != 0) {
		int ret = ep_parse_pass_command(ep, pass);
		if (ret < 0 && ret != PARSE_CONTINUE)
			return ret;

		if (!cf_peek_valid_token(&ep->cfp, &peek))
			return PARSE_EOF;
	}

	/* token is '}' */
	cf_next_token(&ep->cfp);

	return PARSE_SUCCESS;
}
static bool gl_write_mul(struct gl_shader_parser *glsp,
		struct cf_token **p_token)
{
	struct cf_parser *cfp = &glsp->parser.cfp;
	cfp->cur_token = *p_token;

	if (!cf_next_token(cfp))    return false;
	if (!cf_token_is(cfp, "(")) return false;

	dstr_cat(&glsp->gl_string, "(");
	gl_write_function_contents(glsp, &cfp->cur_token, ",");
	dstr_cat(&glsp->gl_string, ") * (");
	cf_next_token(cfp);
	gl_write_function_contents(glsp, &cfp->cur_token, ")");
	dstr_cat(&glsp->gl_string, "))");

	*p_token = cfp->cur_token;
	return true;
}
/* processes texture.Sample(sampler, texcoord) */
static bool gl_write_texture_code(struct gl_shader_parser *glsp,
		struct cf_token **p_token, struct shader_var *var)
{
	struct cf_parser *cfp = &glsp->parser.cfp;
	bool written = false;
	cfp->cur_token = *p_token;

	if (!cf_next_token(cfp))    return false;
	if (!cf_token_is(cfp, ".")) return false;
	if (!cf_next_token(cfp))    return false;

	const char *function_end = ")";

	if (cf_token_is(cfp, "Sample"))
		written = gl_write_texture_call(glsp, var, "texture", true);
	else if (cf_token_is(cfp, "SampleBias"))
		written = gl_write_texture_call(glsp, var, "texture", true);
	else if (cf_token_is(cfp, "SampleGrad"))
		written = gl_write_texture_call(glsp, var, "textureGrad", true);
	else if (cf_token_is(cfp, "SampleLevel"))
		written = gl_write_texture_call(glsp, var, "textureLod", true);
	else if (cf_token_is(cfp, "Load")) {
		written = gl_write_texture_call(glsp, var, "texelFetch", false);
		dstr_cat(&glsp->gl_string, "(");
		function_end = ").xy, 0)";
	}

	if (!written)
		return false;

	if (!cf_next_token(cfp)) return false;

	gl_write_function_contents(glsp, &cfp->cur_token, ")");
	dstr_cat(&glsp->gl_string, function_end);

	*p_token = cfp->cur_token;
	return true;
}
static inline bool gl_write_texture_call(struct gl_shader_parser *glsp,
		struct shader_var *var, const char *call, bool sampler)
{
	struct cf_parser *cfp = &glsp->parser.cfp;
	size_t sampler_id = (size_t)-1;

	if (!cf_next_token(cfp))    return false;
	if (!cf_token_is(cfp, "(")) return false;

	if (sampler) {
		if (!cf_next_token(cfp))    return false;
		sampler_id = sp_getsampler(glsp, cfp->cur_token);
		if (sampler_id == (size_t) -1) return false;
		var->gl_sampler_id = sampler_id;
		if (!cf_next_token(cfp))    return false;
		if (!cf_token_is(cfp, ",")) return false;
	}

	dstr_cat(&glsp->gl_string, call);
	dstr_cat(&glsp->gl_string, "(");
	dstr_cat(&glsp->gl_string, var->name);
	dstr_cat(&glsp->gl_string, ", ");
	return true;
}
Example #7
0
static void ep_parse_function(struct effect_parser *ep,
		char *type, char *name)
{
	struct ep_func func;
	int code;

	ep_func_init(&func, type, name);
	if (ep_getstruct(ep, type))
		da_push_back(func.struct_deps, &func.ret_type);

	if (!ep_parse_func_params(ep, &func))
		goto error;

	if (!cf_next_valid_token(&ep->cfp))
		goto error;

	/* if function is mapped to something, for example COLOR */
	if (cf_token_is(&ep->cfp, ":")) {
		code = cf_next_name(&ep->cfp, &func.mapping,
				"mapping specifier", "{");
		if (code == PARSE_EOF)
			goto error;
		else if (code != PARSE_CONTINUE) {
			if (!cf_next_valid_token(&ep->cfp))
				goto error;
		}
	}

	if (!cf_token_is(&ep->cfp, "{")) {
		cf_adderror_expecting(&ep->cfp, "{");
		goto error;
	}

	if (!ep_parse_func_contents(ep, &func))
		goto error;

	/* it is established that the current token is '}' if we reach this */
	cf_next_token(&ep->cfp);

	da_push_back(ep->funcs, &func);
	return;

error:
	ep_func_free(&func);
}
Example #8
0
static void sp_parse_function(struct shader_parser *sp, char *type, char *name)
{
	struct shader_func func;

	shader_func_init(&func, type, name);
	if (!sp_parse_func_params(sp, &func))
		goto error;

	if (!cf_next_valid_token(&sp->cfp))
		goto error;

	/* if function is mapped to something, for example COLOR */
	if (cf_token_is(&sp->cfp, ":")) {
		char *mapping = NULL;
		int errorcode = cf_next_name(&sp->cfp, &mapping, "mapping",
				"{");
		if (errorcode != PARSE_SUCCESS)
			goto error;

		func.mapping = mapping;

		if (!cf_next_valid_token(&sp->cfp))
			goto error;
	}

	if (!cf_token_is(&sp->cfp, "{")) {
		cf_adderror_expecting(&sp->cfp, "{");
		goto error;
	}

	func.start = sp->cfp.cur_token;
	if (!cf_pass_pair(&sp->cfp, '{', '}'))
		goto error;

	/* it is established that the current token is '}' if we reach this */
	cf_next_token(&sp->cfp);

	func.end = sp->cfp.cur_token;
	da_push_back(sp->funcs, &func);
	return;

error:
	shader_func_free(&func);
}
Example #9
0
static bool sp_parse_func_params(struct shader_parser *sp,
		struct shader_func *func)
{
	struct cf_token peek;
	int code;

	cf_token_clear(&peek);

	if (!cf_peek_valid_token(&sp->cfp, &peek))
		return false;

	if (*peek.str.array == ')') {
		cf_next_token(&sp->cfp);
		goto exit;
	}

	do {
		struct shader_var var;
		shader_var_init(&var);

		if (!cf_token_is(&sp->cfp, "(") && !cf_token_is(&sp->cfp, ","))
			cf_adderror_syntax_error(&sp->cfp);

		code = sp_parse_func_param(sp, &var);
		if (code != PARSE_SUCCESS) {
			shader_var_free(&var);

			if (code == PARSE_CONTINUE)
				goto exit;
			else if (code == PARSE_EOF)
				return false;
		}

		da_push_back(func->params, &var);
	} while (!cf_token_is(&sp->cfp, ")"));

exit:
	return true;
}