authorgravatar for git@vexu.euVeikka Tuominen <git@vexu.eu> 2019-12-29 20:10:20+02:00
committergravatar for git@vexu.euVeikka Tuominen <git@vexu.eu> 2019-12-29 20:19:30+02:00
log950eb81304dedc01ef1500dd2da1458694306b00
treed02476d9903f176468ac2e6267c2b879d8882b83
parentca211617bd6a780037430f170f1c1a730b8aac17
signature Commit is signed but in an unrecognized format.

translate-c-2 macro comparision ops


2 files changed, 110 insertions(+), 43 deletions(-)

src-self-hosted/translate_c.zig+97-43
...@@ -4287,7 +4287,33 @@ fn transMacroFnDefine(c: *Context, it: *ctok.TokenList.Iterator, name: []const u...@@ -4287,7 +4287,33 @@ fn transMacroFnDefine(c: *Context, it: *ctok.TokenList.Iterator, name: []const u
4287const ParseError = Error || error{ParseError};4287const ParseError = Error || error{ParseError};
42884288
4289fn parseCExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: ZigClangSourceLocation, scope: *Scope) ParseError!*ast.Node {4289fn parseCExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: ZigClangSourceLocation, scope: *Scope) ParseError!*ast.Node {
4290 return parseCPrefixOpExpr(c, it, source_loc, scope);4290 const node = try parseCPrefixOpExpr(c, it, source_loc, scope);
4291 switch (it.next().?.id) {
4292 .QuestionMark => {
4293 // must come immediately after expr
4294 _ = try appendToken(c, .RParen, ")");
4295 const if_node = try transCreateNodeIf(c);
4296 if_node.condition = node;
4297 if_node.body = try parseCPrimaryExpr(c, it, source_loc, scope);
4298 if (it.next().?.id != .Colon) {
4299 try failDecl(
4300 c,
4301 source_loc,
4302 it.list.at(0).*.bytes,
4303 "unable to translate C expr: expected ':'",
4304 .{},
4305 );
4306 return error.ParseError;
4307 }
4308 if_node.@"else" = try transCreateNodeElse(c);
4309 if_node.@"else".?.body = try parseCPrimaryExpr(c, it, source_loc, scope);
4310 return &if_node.base;
4311 },
4312 else => {
4313 _ = it.prev();
4314 return node;
4315 },
4316 }
4291}4317}
42924318
4293fn parseCNumLit(c: *Context, tok: *CToken, source_loc: ZigClangSourceLocation) ParseError!*ast.Node {4319fn parseCNumLit(c: *Context, tok: *CToken, source_loc: ZigClangSourceLocation) ParseError!*ast.Node {
...@@ -4532,7 +4558,7 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4532,7 +4558,7 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4532 },4558 },
4533 .Shl => {4559 .Shl => {
4534 const op_token = try appendToken(c, .AngleBracketAngleBracketLeft, "<<");4560 const op_token = try appendToken(c, .AngleBracketAngleBracketLeft, "<<");
4535 const rhs = try parseCExpr(c, it, source_loc, scope);4561 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4536 const bitshift_node = try c.a().create(ast.Node.InfixOp);4562 const bitshift_node = try c.a().create(ast.Node.InfixOp);
4537 bitshift_node.* = .{4563 bitshift_node.* = .{
4538 .op_token = op_token,4564 .op_token = op_token,
...@@ -4543,9 +4569,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4543,9 +4569,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4543 node = &bitshift_node.base;4569 node = &bitshift_node.base;
4544 },4570 },
4545 .Shr => {4571 .Shr => {
4546 const op_token = try appendToken(rp.c, .AngleBracketAngleBracketRight, ">>");4572 const op_token = try appendToken(c, .AngleBracketAngleBracketRight, ">>");
4547 const rhs = try parseCExpr(rp, it, source_loc, scope);4573 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4548 const bitshift_node = try rp.c.a().create(ast.Node.InfixOp);4574 const bitshift_node = try c.a().create(ast.Node.InfixOp);
4549 bitshift_node.* = .{4575 bitshift_node.* = .{
4550 .op_token = op_token,4576 .op_token = op_token,
4551 .lhs = node,4577 .lhs = node,
...@@ -4556,7 +4582,7 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4556,7 +4582,7 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4556 },4582 },
4557 .Pipe => {4583 .Pipe => {
4558 const op_token = try appendToken(c, .Pipe, "|");4584 const op_token = try appendToken(c, .Pipe, "|");
4559 const rhs = try parseCExpr(c, it, source_loc, scope);4585 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4560 const or_node = try c.a().create(ast.Node.InfixOp);4586 const or_node = try c.a().create(ast.Node.InfixOp);
4561 or_node.* = .{4587 or_node.* = .{
4562 .op_token = op_token,4588 .op_token = op_token,
...@@ -4567,9 +4593,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4567,9 +4593,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4567 node = &or_node.base;4593 node = &or_node.base;
4568 },4594 },
4569 .Ampersand => {4595 .Ampersand => {
4570 const op_token = try appendToken(rp.c, .Ampersand, "&");4596 const op_token = try appendToken(c, .Ampersand, "&");
4571 const rhs = try parseCExpr(rp, it, source_loc, scope);4597 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4572 const bitand_node = try rp.c.a().create(ast.Node.InfixOp);4598 const bitand_node = try c.a().create(ast.Node.InfixOp);
4573 bitand_node.* = .{4599 bitand_node.* = .{
4574 .op_token = op_token,4600 .op_token = op_token,
4575 .lhs = node,4601 .lhs = node,
...@@ -4579,9 +4605,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4579,9 +4605,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4579 node = &bitand_node.base;4605 node = &bitand_node.base;
4580 },4606 },
4581 .Plus => {4607 .Plus => {
4582 const op_token = try appendToken(rp.c, .Plus, "+");4608 const op_token = try appendToken(c, .Plus, "+");
4583 const rhs = try parseCExpr(rp, it, source_loc, scope);4609 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4584 const add_node = try rp.c.a().create(ast.Node.InfixOp);4610 const add_node = try c.a().create(ast.Node.InfixOp);
4585 add_node.* = .{4611 add_node.* = .{
4586 .op_token = op_token,4612 .op_token = op_token,
4587 .lhs = node,4613 .lhs = node,
...@@ -4591,9 +4617,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4591,9 +4617,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4591 node = &add_node.base;4617 node = &add_node.base;
4592 },4618 },
4593 .Minus => {4619 .Minus => {
4594 const op_token = try appendToken(rp.c, .Minus, "-");4620 const op_token = try appendToken(c, .Minus, "-");
4595 const rhs = try parseCExpr(rp, it, source_loc, scope);4621 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4596 const sub_node = try rp.c.a().create(ast.Node.InfixOp);4622 const sub_node = try c.a().create(ast.Node.InfixOp);
4597 sub_node.* = .{4623 sub_node.* = .{
4598 .op_token = op_token,4624 .op_token = op_token,
4599 .lhs = node,4625 .lhs = node,
...@@ -4603,9 +4629,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4603,9 +4629,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4603 node = &sub_node.base;4629 node = &sub_node.base;
4604 },4630 },
4605 .And => {4631 .And => {
4606 const op_token = try appendToken(rp.c, .Keyword_and, "and");4632 const op_token = try appendToken(c, .Keyword_and, "and");
4607 const rhs = try parseCExpr(rp, it, source_loc, scope);4633 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4608 const and_node = try rp.c.a().create(ast.Node.InfixOp);4634 const and_node = try c.a().create(ast.Node.InfixOp);
4609 and_node.* = .{4635 and_node.* = .{
4610 .op_token = op_token,4636 .op_token = op_token,
4611 .lhs = node,4637 .lhs = node,
...@@ -4615,9 +4641,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4615,9 +4641,9 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4615 node = &and_node.base;4641 node = &and_node.base;
4616 },4642 },
4617 .Or => {4643 .Or => {
4618 const op_token = try appendToken(rp.c, .Keyword_or, "or");4644 const op_token = try appendToken(c, .Keyword_or, "or");
4619 const rhs = try parseCExpr(rp, it, source_loc, scope);4645 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4620 const or_node = try rp.c.a().create(ast.Node.InfixOp);4646 const or_node = try c.a().create(ast.Node.InfixOp);
4621 or_node.* = .{4647 or_node.* = .{
4622 .op_token = op_token,4648 .op_token = op_token,
4623 .lhs = node,4649 .lhs = node,
...@@ -4626,9 +4652,57 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4626,9 +4652,57 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4626 };4652 };
4627 node = &or_node.base;4653 node = &or_node.base;
4628 },4654 },
4655 .Gt => {
4656 const op_token = try appendToken(c, .AngleBracketRight, ">");
4657 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4658 const and_node = try c.a().create(ast.Node.InfixOp);
4659 and_node.* = .{
4660 .op_token = op_token,
4661 .lhs = node,
4662 .op = .GreaterThan,
4663 .rhs = rhs,
4664 };
4665 node = &and_node.base;
4666 },
4667 .Gte => {
4668 const op_token = try appendToken(c, .AngleBracketRightEqual, ">=");
4669 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4670 const and_node = try c.a().create(ast.Node.InfixOp);
4671 and_node.* = .{
4672 .op_token = op_token,
4673 .lhs = node,
4674 .op = .GreaterOrEqual,
4675 .rhs = rhs,
4676 };
4677 node = &and_node.base;
4678 },
4679 .Lt => {
4680 const op_token = try appendToken(c, .AngleBracketLeft, "<");
4681 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4682 const and_node = try c.a().create(ast.Node.InfixOp);
4683 and_node.* = .{
4684 .op_token = op_token,
4685 .lhs = node,
4686 .op = .LessThan,
4687 .rhs = rhs,
4688 };
4689 node = &and_node.base;
4690 },
4691 .Lte => {
4692 const op_token = try appendToken(c, .AngleBracketLeftEqual, "<=");
4693 const rhs = try parseCPrefixOpExpr(c, it, source_loc, scope);
4694 const and_node = try c.a().create(ast.Node.InfixOp);
4695 and_node.* = .{
4696 .op_token = op_token,
4697 .lhs = node,
4698 .op = .LessOrEqual,
4699 .rhs = rhs,
4700 };
4701 node = &and_node.base;
4702 },
4629 .LBrace => {4703 .LBrace => {
4630 const arr_node = try transCreateNodeArrayAccess(c, node);4704 const arr_node = try transCreateNodeArrayAccess(c, node);
4631 arr_node.op.ArrayAccess = try parseCExpr(c, it, source_loc, scope);4705 arr_node.op.ArrayAccess = try parseCPrefixOpExpr(c, it, source_loc, scope);
4632 arr_node.rtoken = try appendToken(c, .RBrace, "]");4706 arr_node.rtoken = try appendToken(c, .RBrace, "]");
4633 node = &arr_node.base;4707 node = &arr_node.base;
4634 if (it.next().?.id != .RBrace) {4708 if (it.next().?.id != .RBrace) {
...@@ -4645,7 +4719,7 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4645,7 +4719,7 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4645 .LParen => {4719 .LParen => {
4646 const call_node = try transCreateNodeFnCall(c, node);4720 const call_node = try transCreateNodeFnCall(c, node);
4647 while (true) {4721 while (true) {
4648 const arg = try parseCExpr(c, it, source_loc, scope);4722 const arg = try parseCPrefixOpExpr(c, it, source_loc, scope);
4649 try call_node.op.Call.params.push(arg);4723 try call_node.op.Call.params.push(arg);
4650 const next = it.next().?;4724 const next = it.next().?;
4651 if (next.id == .Comma)4725 if (next.id == .Comma)
...@@ -4666,26 +4740,6 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig...@@ -4666,26 +4740,6 @@ fn parseCSuffixOpExpr(c: *Context, it: *ctok.TokenList.Iterator, source_loc: Zig
4666 call_node.rtoken = try appendToken(c, .RParen, ")");4740 call_node.rtoken = try appendToken(c, .RParen, ")");
4667 node = &call_node.base;4741 node = &call_node.base;
4668 },4742 },
4669 .QuestionMark => {
4670 // must come immediately after expr
4671 _ = try appendToken(c, .RParen, ")");
4672 const if_node = try transCreateNodeIf(c);
4673 if_node.condition = node;
4674 if_node.body = try parseCPrimaryExpr(c, it, source_loc, scope);
4675 if (it.next().?.id != .Colon) {
4676 try failDecl(
4677 c,
4678 source_loc,
4679 it.list.at(0).*.bytes,
4680 "unable to translate C expr: expected ':'",
4681 .{},
4682 );
4683 return error.ParseError;
4684 }
4685 if_node.@"else" = try transCreateNodeElse(c);
4686 if_node.@"else".?.body = try parseCPrimaryExpr(c, it, source_loc, scope);
4687 node = &if_node.base;
4688 },
4689 else => {4743 else => {
4690 _ = it.prev();4744 _ = it.prev();
4691 return node;4745 return node;
test/translate_c.zig+13
...@@ -2219,4 +2219,17 @@ pub fn addCases(cases: *tests.TranslateCContext) void {...@@ -2219,4 +2219,17 @@ pub fn addCases(cases: *tests.TranslateCContext) void {
2219 \\ };2219 \\ };
2220 \\}2220 \\}
2221 });2221 });
2222
2223 cases.add("macro comparisions",
2224 \\#define MIN(a, b) ((b) < (a) ? (b) : (a))
2225 \\#define MAX(a, b) ((b) > (a) ? (b) : (a))
2226 , &[_][]const u8{
2227 \\pub inline fn MIN(a: var, b: var) @TypeOf(if (b < a) b else a) {
2228 \\ return if (b < a) b else a;
2229 \\}
2230 ,
2231 \\pub inline fn MAX(a: var, b: var) @TypeOf(if (b > a) b else a) {
2232 \\ return if (b > a) b else a;
2233 \\}
2234 });
2222}2235}