~sircmpwn/hare-dev

This thread contains a patchset. You're looking at the original emails, but you may wish to use the patch review UI. Review patch
2 2

[PATCH harec v2] check: verify define compatibility

Details
Message ID
<20230207184606.27520-1-tb46305@gmail.com>
DKIM signature
missing
Download raw message
Patch: +35 -3
Signed-off-by: Armin Weigl <tb46305@gmail.com>
---
v2:
	rebase
	improved error message
 src/check.c         | 36 ++++++++++++++++++++++++++++++++++--
 tests/36-defines.ha |  2 +-
 2 files changed, 35 insertions(+), 3 deletions(-)

diff --git a/src/check.c b/src/check.c
index 5440134..acfb566 100644
--- a/src/check.c
+++ b/src/check.c
@@ -3313,11 +3313,24 @@ check_expression(struct context *ctx,
static struct declaration *
check_const(struct context *ctx,
	const struct scope_object *obj,
	const struct location *loc,
	const struct ast_global_decl *adecl)
{
	struct declaration *decl = xcalloc(1, sizeof(struct declaration));
	const struct scope_object *shadow_obj = scope_lookup(
			ctx->defines, &adecl->ident);
	if (obj != shadow_obj) {
		// Shadowed by define
		if (obj->type != shadow_obj->type) {
			char *typename = gen_typename(obj->type);
			char *shadow_typename = gen_typename(shadow_obj->type);
			error(ctx, *loc, NULL,
					"constant of type %s is shadowed by define of incompatible type %s",
					typename, shadow_typename);
			free(typename);
			free(shadow_typename);
		}
	}
	decl->type = DECL_CONST;
	decl->constant.type = obj->type;
	decl->constant.value = shadow_obj->value;
@@ -3491,7 +3504,7 @@ check_declaration(struct context *ctx,
	struct declaration *decl = NULL;
	switch (adecl->decl_type) {
	case AST_DECL_CONST:
		decl = check_const(ctx, &idecl->obj, &adecl->constant);
		decl = check_const(ctx, &idecl->obj, &adecl->loc, &adecl->constant);
		break;
	case AST_DECL_FUNC:
		decl = check_function(ctx, &idecl->obj, adecl);
@@ -4304,9 +4317,28 @@ check_internal(struct type_store *ts,
		scan_enum_field_aliases(&ctx, obj);
	}

	// XXX: shadowed declarations are not checked for consistency
	ctx.scope = ctx.defines;

	for (const struct scope_object *obj = ctx.scope->objects;
			obj; obj = obj->lnext) {
		const struct scope_object *shadowed_obj =
			scope_lookup(ctx.unit, &obj->name);
		if (!shadowed_obj) {
			continue;
		}
		if (shadowed_obj->otype == O_CONST) {
			continue;
		}
		if (shadowed_obj->otype == O_SCAN) {
			const struct incomplete_declaration *idecl =
				(struct incomplete_declaration *)shadowed_obj;
			if (idecl->decl.decl_type == AST_DECL_CONST) {
				continue;
			}
		}
		error(&ctx, defineloc, NULL, "define shadows non define");
	}

	struct declarations **next_decl = &unit->declarations;
	// Perform actual declaration resolution
	for (const struct scope_object *obj = ctx.unit->objects;
diff --git a/tests/36-defines.ha b/tests/36-defines.ha
index 90be8b5..c53d544 100644
--- a/tests/36-defines.ha
+++ b/tests/36-defines.ha
@@ -47,5 +47,5 @@ export fn main() void = {
	import();
	mandatory();
	optional();
	// TODO: compatibility();
	compatibility();
};

base-commit: 6ef434af84cd0e9d22951ea94e86c11698033294
-- 
2.39.1

[harec/patches] build success

builds.sr.ht <builds@sr.ht>
Details
Message ID
<CQCK0C5XRVVN.2FQ8IUX6J6693@cirno2>
In-Reply-To
<20230207184606.27520-1-tb46305@gmail.com> (view parent)
DKIM signature
missing
Download raw message
harec/patches: SUCCESS in 2m39s

[check: verify define compatibility][0] v2 from [Armin Weigl][1]

[0]: https://lists.sr.ht/~sircmpwn/hare-dev/patches/38806
[1]: tb46305@gmail.com

✓ #936327 SUCCESS harec/patches/netbsd.yml  https://builds.sr.ht/~sircmpwn/job/936327
✓ #936325 SUCCESS harec/patches/alpine.yml  https://builds.sr.ht/~sircmpwn/job/936325
✓ #936326 SUCCESS harec/patches/freebsd.yml https://builds.sr.ht/~sircmpwn/job/936326
Details
Message ID
<CQCRW0GWTJ0P.3KKEXSYJLL02B@attila>
In-Reply-To
<20230207184606.27520-1-tb46305@gmail.com> (view parent)
DKIM signature
missing
Download raw message
> -	// XXX: shadowed declarations are not checked for consistency

While these patches are certainly an improvement, this comment sadly still
applies, because define shadowing isn't entirely solved yet:

file zerodiv.ha:

def X:int = 10/Y;
def Y:int = 2;

fn main() void = {
        static assert(X == 5);
};

Compiling this with harec -D"X:int=5" -D"Y:int=0" complains about division by
zero even though both the file without defines and file with both defines are
perfectly valid, because the shadowing isn't "atomic". I found out
about this a while ago but wasn't able to think of nice a solution and then
completely forgot about it until just now. It's a very low priority thing, so
I'm fine with merging this patch without fixing it, but I'd still like to see
it fixed before we remove that comment and start considering define shadowing
"solved".

> +		const struct scope_object *shadowed_obj =
> +			scope_lookup(ctx.unit, &obj->name);
> +		if (!shadowed_obj) {
> +			continue;
> +		}
> +		if (shadowed_obj->otype == O_CONST) {
> +			continue;
> +		}
> +		if (shadowed_obj->otype == O_SCAN) {
> +			const struct incomplete_declaration *idecl =
> +				(struct incomplete_declaration *)shadowed_obj;
> +			if (idecl->decl.decl_type == AST_DECL_CONST) {

You should ensure idecl->type == IDECL_DECL before reading idecl->decl,
otherwise weird stuff may happen with enum values. Adding a test ensuring those
cannot be shadowed to compatibility() would also be nice.
Reply to thread Export thread (mbox)