summaryrefslogtreecommitdiffstatshomepage
diff options
context:
space:
mode:
authorLuc Van Oostenryck <luc.vanoostenryck@gmail.com>2019-01-17 22:58:01 +0100
committerLuc Van Oostenryck <luc.vanoostenryck@gmail.com>2019-09-27 02:17:34 +0200
commit7aeb06b4bff797da4ea85a18738a2fd1f660d744 (patch)
tree6955efba6e8474607407b1df654911f1216555c7
parent62308ab6a6025f8df926b8af009f68fbebe040b6 (diff)
downloadsparse-7aeb06b4bff797da4ea85a18738a2fd1f660d744.tar.gz
asm: check earlier that body & constraints are strings
The syntax of extended ASM statements requires that the bodies & constraints are given via a literal string. However, at parsing time more general expressions are accepted and it's checked only at evaluation time if these are effectively string literals. This has at least two drawbacks: *) evaluate_asm_statement() is slightly more complicated than needed, mixing these checks with the real evaluation code *) in case of error, the diagnostic is issued later than other syntaxic warnings. Fix this by checking at parse-time that ASM bodies & constraints are string literals and not some arbitrary expressions. Signed-off-by: Luc Van Oostenryck <luc.vanoostenryck@gmail.com>
-rw-r--r--evaluate.c14
-rw-r--r--parse.c7
-rw-r--r--validation/asm-bad0.c6
3 files changed, 10 insertions, 17 deletions
diff --git a/evaluate.c b/evaluate.c
index 70d76523..634da4b9 100644
--- a/evaluate.c
+++ b/evaluate.c
@@ -3523,20 +3523,15 @@ static void evaluate_asm_statement(struct statement *stmt)
struct symbol *sym;
expr = stmt->asm_string;
- if (!expr || expr->type != EXPR_STRING) {
- sparse_error(stmt->pos, "need constant string for inline asm");
+ if (!expr)
return;
- }
FOR_EACH_PTR(stmt->asm_outputs, op) {
/* Identifier */
/* Constraint */
expr = op->constraint;
- if (!expr || expr->type != EXPR_STRING) {
- sparse_error(expr ? expr->pos : stmt->pos, "asm output constraint is not a string");
- op->constraint = NULL;
- } else
+ if (expr)
verify_output_constraint(expr, expr->string->data);
/* Expression */
@@ -3553,10 +3548,7 @@ static void evaluate_asm_statement(struct statement *stmt)
/* Constraint */
expr = op->constraint;
- if (!expr || expr->type != EXPR_STRING) {
- sparse_error(expr ? expr->pos : stmt->pos, "asm input constraint is not a string");
- op->constraint = NULL;
- } else
+ if (expr)
verify_input_constraint(expr, expr->string->data);
/* Expression */
diff --git a/parse.c b/parse.c
index 401f91a1..23c0ee01 100644
--- a/parse.c
+++ b/parse.c
@@ -2050,7 +2050,8 @@ static struct token *parse_asm_operands(struct token *token, struct statement *s
op->name = token->next->next->ident;
token = token->next->next->next;
}
- token = primary_expression(token->next, &op->constraint);
+ token = token->next;
+ token = string_expression(token, &op->constraint, "asm constraint");
token = parens_expression(token, &op->expr, "in asm parameter");
add_expression(inout, op);
} while (match_op(token, ','));
@@ -2101,7 +2102,7 @@ static struct token *parse_asm_statement(struct token *token, struct statement *
token = token->next;
}
token = expect(token, '(', "after asm");
- token = parse_expression(token, &stmt->asm_string);
+ token = string_expression(token, &stmt->asm_string, "inline asm");
if (match_op(token, ':'))
token = parse_asm_operands(token, stmt, &stmt->asm_outputs);
if (match_op(token, ':'))
@@ -2118,7 +2119,7 @@ static struct token *parse_asm_declarator(struct token *token, struct decl_state
{
struct expression *expr;
token = expect(token, '(', "after asm");
- token = parse_expression(token->next, &expr);
+ token = string_expression(token, &expr, "inline asm");
token = expect(token, ')', "after asm");
return token;
}
diff --git a/validation/asm-bad0.c b/validation/asm-bad0.c
index fcd9b1c4..aa9bf28d 100644
--- a/validation/asm-bad0.c
+++ b/validation/asm-bad0.c
@@ -30,12 +30,12 @@ static void iexpr(void)
* check-name: asm-bad0
*
* check-error-start
+asm-bad0.c:6:13: error: string literal expected for inline asm
+asm-bad0.c:11:32: error: string literal expected for asm constraint
+asm-bad0.c:16:49: error: string literal expected for asm constraint
asm-bad0.c:21:41: error: Expected ] at end of array dereference
asm-bad0.c:21:41: error: got )
asm-bad0.c:26:59: error: Expected ] at end of array dereference
asm-bad0.c:26:59: error: got )
-asm-bad0.c:6:9: error: need constant string for inline asm
-asm-bad0.c:11:32: error: asm output constraint is not a string
-asm-bad0.c:16:49: error: asm input constraint is not a string
* check-error-end
*/