| author | |
| committer | |
| log | d7902707bcc1faede9ef5490d02bcea935e3b8fc |
| tree | 244557b0172b781f1dcaa6b2538cf9e515943576 |
| parent | 7b5fb79b5b9625a1c2b7359c6653653a799ca114 |
| signature |
2 files changed, 54 insertions(+), 18 deletions(-)
src-self-hosted/translate_c.zig+35-15| ... | ... | @@ -5479,18 +5479,20 @@ fn parseCPrimaryExpr(c: *Context, it: *CTokenList.Iterator, source: []const u8, |
| 5479 | 5479 | .LParen => { |
| 5480 | 5480 | const inner_node = try parseCExpr(c, it, source, source_loc, scope); |
| 5481 | 5481 | |
| 5482 | if (it.next().?.id != .RParen) { | |
| 5482 | const next_id = it.next().?.id; | |
| 5483 | if (next_id != .RParen) { | |
| 5483 | 5484 | const first_tok = it.list.at(0); |
| 5484 | 5485 | try failDecl( |
| 5485 | 5486 | c, |
| 5486 | 5487 | source_loc, |
| 5487 | 5488 | source[first_tok.start..first_tok.end], |
| 5488 | "unable to translate C expr: expected ')'' here", | |
| 5489 | .{}, | |
| 5489 | "unable to translate C expr: expected ')'' instead got: {}", | |
| 5490 | .{@tagName(next_id)}, | |
| 5490 | 5491 | ); |
| 5491 | 5492 | return error.ParseError; |
| 5492 | 5493 | } |
| 5493 | 5494 | var saw_l_paren = false; |
| 5495 | var saw_integer_literal = false; | |
| 5494 | 5496 | switch (it.peek().?.id) { |
| 5495 | 5497 | // (type)(to_cast) |
| 5496 | 5498 | .LParen => { |
| ... | ... | @@ -5499,6 +5501,10 @@ fn parseCPrimaryExpr(c: *Context, it: *CTokenList.Iterator, source: []const u8, |
| 5499 | 5501 | }, |
| 5500 | 5502 | // (type)identifier |
| 5501 | 5503 | .Identifier => {}, |
| 5504 | // (type)integer | |
| 5505 | .IntegerLiteral => { | |
| 5506 | saw_integer_literal = true; | |
| 5507 | }, | |
| 5502 | 5508 | else => return inner_node, |
| 5503 | 5509 | } |
| 5504 | 5510 | |
| ... | ... | @@ -5519,6 +5525,15 @@ fn parseCPrimaryExpr(c: *Context, it: *CTokenList.Iterator, source: []const u8, |
| 5519 | 5525 | return error.ParseError; |
| 5520 | 5526 | } |
| 5521 | 5527 | |
| 5528 | if (saw_integer_literal) { | |
| 5529 | // @intToPtr(dest, x) | |
| 5530 | const int_to_ptr = try transCreateNodeBuiltinFnCall(c, "@intToPtr"); | |
| 5531 | try int_to_ptr.params.push(inner_node); | |
| 5532 | try int_to_ptr.params.push(node_to_cast); | |
| 5533 | int_to_ptr.rparen_token = try appendToken(c, .RParen, ")"); | |
| 5534 | return &int_to_ptr.base; | |
| 5535 | } | |
| 5536 | ||
| 5522 | 5537 | //( if (@typeInfo(@TypeOf(x)) == .Pointer) |
| 5523 | 5538 | // @ptrCast(dest, @alignCast(@alignOf(dest.Child), x)) |
| 5524 | 5539 | //else if (@typeInfo(@TypeOf(x)) == .Integer and @typeInfo(dest) == .Pointer)) |
| ... | ... | @@ -5750,19 +5765,24 @@ fn parseCSuffixOpExpr(c: *Context, it: *CTokenList.Iterator, source: []const u8, |
| 5750 | 5765 | // hack to get zig fmt to render a comma in builtin calls |
| 5751 | 5766 | _ = try appendToken(c, .Comma, ","); |
| 5752 | 5767 | |
| 5753 | const ptr_kind = blk: { | |
| 5754 | // * token | |
| 5755 | _ = it.prev(); | |
| 5756 | // last token of `node` | |
| 5757 | const prev_id = it.prev().?.id; | |
| 5758 | _ = it.next(); | |
| 5759 | _ = it.next(); | |
| 5760 | break :blk if (prev_id == .Keyword_void) .Asterisk else Token.Id.Identifier; | |
| 5761 | }; | |
| 5768 | // * token | |
| 5769 | _ = it.prev(); | |
| 5770 | // last token of `node` | |
| 5771 | const prev_id = it.prev().?.id; | |
| 5772 | _ = it.next(); | |
| 5773 | _ = it.next(); | |
| 5762 | 5774 | |
| 5763 | const ptr = try transCreateNodePtrType(c, false, false, ptr_kind); | |
| 5764 | ptr.rhs = node; | |
| 5765 | return &ptr.base; | |
| 5775 | if (prev_id == .Keyword_void) { | |
| 5776 | const ptr = try transCreateNodePtrType(c, false, false, .Asterisk); | |
| 5777 | ptr.rhs = node; | |
| 5778 | const optional_node = try transCreateNodePrefixOp(c, .OptionalType, .QuestionMark, "?"); | |
| 5779 | optional_node.rhs = &ptr.base; | |
| 5780 | return &optional_node.base; | |
| 5781 | } else { | |
| 5782 | const ptr = try transCreateNodePtrType(c, false, false, Token.Id.Identifier); | |
| 5783 | ptr.rhs = node; | |
| 5784 | return &ptr.base; | |
| 5785 | } | |
| 5766 | 5786 | } else { |
| 5767 | 5787 | // expr * expr |
| 5768 | 5788 | op_token = try appendToken(c, .Asterisk, "*"); |
test/translate_c.zig+19-3| ... | ... | @@ -2668,11 +2668,11 @@ pub fn addCases(cases: *tests.TranslateCContext) void { |
| 2668 | 2668 | \\#define FOO(bar) baz((void *)(baz)) |
| 2669 | 2669 | \\#define BAR (void*) a |
| 2670 | 2670 | , &[_][]const u8{ |
| 2671 | \\pub inline fn FOO(bar: var) @TypeOf(baz((if (@typeInfo(@TypeOf(baz)) == .Pointer) @ptrCast(*c_void, @alignCast(@alignOf(*c_void.Child), baz)) else if (@typeInfo(@TypeOf(baz)) == .Int and @typeInfo(*c_void) == .Pointer) @intToPtr(*c_void, baz) else @as(*c_void, baz)))) { | |
| 2672 | \\ return baz((if (@typeInfo(@TypeOf(baz)) == .Pointer) @ptrCast(*c_void, @alignCast(@alignOf(*c_void.Child), baz)) else if (@typeInfo(@TypeOf(baz)) == .Int and @typeInfo(*c_void) == .Pointer) @intToPtr(*c_void, baz) else @as(*c_void, baz))); | |
| 2671 | \\pub inline fn FOO(bar: var) @TypeOf(baz((if (@typeInfo(@TypeOf(baz)) == .Pointer) @ptrCast(?*c_void, @alignCast(@alignOf(?*c_void.Child), baz)) else if (@typeInfo(@TypeOf(baz)) == .Int and @typeInfo(?*c_void) == .Pointer) @intToPtr(?*c_void, baz) else @as(?*c_void, baz)))) { | |
| 2672 | \\ return baz((if (@typeInfo(@TypeOf(baz)) == .Pointer) @ptrCast(?*c_void, @alignCast(@alignOf(?*c_void.Child), baz)) else if (@typeInfo(@TypeOf(baz)) == .Int and @typeInfo(?*c_void) == .Pointer) @intToPtr(?*c_void, baz) else @as(?*c_void, baz))); | |
| 2673 | 2673 | \\} |
| 2674 | 2674 | , |
| 2675 | \\pub const BAR = (if (@typeInfo(@TypeOf(a)) == .Pointer) @ptrCast(*c_void, @alignCast(@alignOf(*c_void.Child), a)) else if (@typeInfo(@TypeOf(a)) == .Int and @typeInfo(*c_void) == .Pointer) @intToPtr(*c_void, a) else @as(*c_void, a)); | |
| 2675 | \\pub const BAR = (if (@typeInfo(@TypeOf(a)) == .Pointer) @ptrCast(?*c_void, @alignCast(@alignOf(?*c_void.Child), a)) else if (@typeInfo(@TypeOf(a)) == .Int and @typeInfo(?*c_void) == .Pointer) @intToPtr(?*c_void, a) else @as(?*c_void, a)); | |
| 2676 | 2676 | }); |
| 2677 | 2677 | |
| 2678 | 2678 | cases.add("macro conditional operator", |
| ... | ... | @@ -2894,4 +2894,20 @@ pub fn addCases(cases: *tests.TranslateCContext) void { |
| 2894 | 2894 | \\ return (if (@typeInfo(@TypeOf(dpy)) == .Pointer) @ptrCast(_XPrivDisplay, @alignCast(@alignOf(_XPrivDisplay.Child), dpy)) else if (@typeInfo(@TypeOf(dpy)) == .Int and @typeInfo(_XPrivDisplay) == .Pointer) @intToPtr(_XPrivDisplay, dpy) else @as(_XPrivDisplay, dpy)).*.default_screen; |
| 2895 | 2895 | \\} |
| 2896 | 2896 | }); |
| 2897 | ||
| 2898 | cases.add("Cast from integer literals to poiter", | |
| 2899 | \\#define NULL ((void*)0) | |
| 2900 | \\#define GPIO_0_MEM_MAP ((unsigned*)0x8000) | |
| 2901 | \\#define GPIO_1_MEM_MAP ((unsigned*)0x8004) | |
| 2902 | \\#define GPIO_2_MEM_MAP ((unsigned*)0x8008) | |
| 2903 | \\ | |
| 2904 | , &[_][]const u8{ | |
| 2905 | \\pub const NULL = @intToPtr(?*c_void, 0); | |
| 2906 | , | |
| 2907 | \\pub const GPIO_0_MEM_MAP = @intToPtr([*c]c_uint, 0x8000); | |
| 2908 | , | |
| 2909 | \\pub const GPIO_1_MEM_MAP = @intToPtr([*c]c_uint, 0x8004); | |
| 2910 | , | |
| 2911 | \\pub const GPIO_2_MEM_MAP = @intToPtr([*c]c_uint, 0x8008); | |
| 2912 | }); | |
| 2897 | 2913 | } |