shithub: scc

Download patch

ref: b1b5c5787733eefb5d185743b368a4eef483aae9
parent: e7de88b1568b84cdd7c18b3149d7e17f8686763b
author: Roberto E. Vargas Caballero <k0ga@shike2.com>
date: Sat Oct 30 12:46:53 EDT 2021

cc1: Fix type conversion

Casts to void were disallow, and the logic in the function
was really confusing. This new version enables any conversion
to void and simplifies a lot the code.

--- a/src/cmd/cc/cc1/expr.c
+++ b/src/cmd/cc/cc1/expr.c
@@ -242,48 +242,39 @@
 convert(Node *np, Type *newtp, int iscast)
 {
 	Type *oldtp = np->type;
+	int op = newtp->op;
 
 	if (eqtype(newtp, oldtp, 0))
 		return np;
+	if (iscast && op == VOID)
+		goto good_conv;
 
 	switch (oldtp->op) {
 	case ENUM:
 	case INT:
+		if (op == PTR && (iscast || cmpnode(np, 0)))
+			goto good_conv;
 	case FLOAT:
-		switch (newtp->op) {
-		case PTR:
-			if (oldtp->op == FLOAT || !cmpnode(np, 0) && !iscast)
-				return NULL;
-		case INT:
-		case FLOAT:
-		case ENUM:
-			break;
-		default:
-			return NULL;
-		}
-		break;
+		if (op == INT || op == FLOAT || op == ENUM)
+			goto good_conv;
+		return NULL;
 	case PTR:
-		switch (newtp->op) {
-		case ENUM:
-		case INT:
-		case VOID:
-			if (!iscast)
-				return NULL;
-			break;
-		case PTR:
-			if (eqtype(newtp, oldtp, 1) ||
-			    iscast ||
-			    newtp == pvoidtype || oldtp == pvoidtype) {
-				np->type = newtp;
-				return np;
-			}
-		default:
-			return NULL;
+		if (op == ENUM || op == INT) {
+			if (iscast)
+				goto good_conv;
+		} else if (op == PTR) {
+			if (eqtype(newtp, oldtp, 1))
+				goto good_conv;
+			if (iscast)
+				goto good_conv;
+			if (newtp == pvoidtype || oldtp == pvoidtype)
+				goto good_conv;
 		}
-		break;
 	default:
 		return NULL;
 	}
+
+good_conv:
 	return node(OCAST, newtp, np, NULL);
 }