| ... | @@ -1226,8 +1226,8 @@ static AstNode *trans_compound_stmt(Context *c, TransScope *scope, const clang:: | ... | @@ -1226,8 +1226,8 @@ static AstNode *trans_compound_stmt(Context *c, TransScope *scope, const clang:: |
| 1226 | return child_scope_block->node; | 1226 | return child_scope_block->node; |
| 1227 | } | 1227 | } |
| 1228 | | 1228 | |
| 1229 | static AstNode *trans_stmt_expr(Context *c, TransScope *scope, const clang::StmtExpr *stmt, | 1229 | static AstNode *trans_stmt_expr(Context *c, ResultUsed result_used, TransScope *scope, |
| 1230 | TransScope **out_node_scope) | 1230 | const clang::StmtExpr *stmt, TransScope **out_node_scope) |
| 1231 | { | 1231 | { |
| 1232 | AstNode *block = trans_compound_stmt(c, scope, stmt->getSubStmt(), out_node_scope); | 1232 | AstNode *block = trans_compound_stmt(c, scope, stmt->getSubStmt(), out_node_scope); |
| 1233 | if (block == nullptr) | 1233 | if (block == nullptr) |
| ... | @@ -1248,7 +1248,7 @@ static AstNode *trans_stmt_expr(Context *c, TransScope *scope, const clang::Stmt | ... | @@ -1248,7 +1248,7 @@ static AstNode *trans_stmt_expr(Context *c, TransScope *scope, const clang::Stmt |
| 1248 | return_expr = return_expr->data.bin_op_expr.op2; | 1248 | return_expr = return_expr->data.bin_op_expr.op2; |
| 1249 | } | 1249 | } |
| 1250 | block->data.block.statements.append(trans_create_node_break(c, label, return_expr)); | 1250 | block->data.block.statements.append(trans_create_node_break(c, label, return_expr)); |
| 1251 | return block; | 1251 | return maybe_suppress_result(c, result_used, block); |
| 1252 | } | 1252 | } |
| 1253 | | 1253 | |
| 1254 | static AstNode *trans_return_stmt(Context *c, TransScope *scope, const clang::ReturnStmt *stmt) { | 1254 | static AstNode *trans_return_stmt(Context *c, TransScope *scope, const clang::ReturnStmt *stmt) { |
| ... | @@ -1264,13 +1264,15 @@ static AstNode *trans_return_stmt(Context *c, TransScope *scope, const clang::Re | ... | @@ -1264,13 +1264,15 @@ static AstNode *trans_return_stmt(Context *c, TransScope *scope, const clang::Re |
| 1264 | } | 1264 | } |
| 1265 | } | 1265 | } |
| 1266 | | 1266 | |
| 1267 | static AstNode *trans_integer_literal(Context *c, const clang::IntegerLiteral *stmt) { | 1267 | static AstNode *trans_integer_literal(Context *c, ResultUsed result_used, const clang::IntegerLiteral *stmt) { |
| 1268 | llvm::APSInt result; | 1268 | llvm::APSInt result; |
| 1269 | if (!stmt->EvaluateAsInt(result, *reinterpret_cast<clang::ASTContext *>(c->ctx))) { | 1269 | if (!stmt->EvaluateAsInt(result, *reinterpret_cast<clang::ASTContext *>(c->ctx))) { |
| 1270 | emit_warning(c, stmt->getLocStart(), "invalid integer literal"); | 1270 | emit_warning(c, stmt->getLocStart(), "invalid integer literal"); |
| 1271 | return nullptr; | 1271 | return nullptr; |
| 1272 | } | 1272 | } |
| 1273 | return trans_create_node_apint(c, result); | 1273 | |
| | 1274 | AstNode *node = trans_create_node_apint(c, result); |
| | 1275 | return maybe_suppress_result(c, result_used, node); |
| 1274 | } | 1276 | } |
| 1275 | | 1277 | |
| 1276 | static AstNode *trans_conditional_operator(Context *c, ResultUsed result_used, TransScope *scope, | 1278 | static AstNode *trans_conditional_operator(Context *c, ResultUsed result_used, TransScope *scope, |
| ... | @@ -1407,14 +1409,17 @@ static AstNode *trans_binary_operator(Context *c, ResultUsed result_used, TransS | ... | @@ -1407,14 +1409,17 @@ static AstNode *trans_binary_operator(Context *c, ResultUsed result_used, TransS |
| 1407 | case clang::BO_Cmp: | 1409 | case clang::BO_Cmp: |
| 1408 | emit_warning(c, stmt->getLocStart(), "TODO handle more C binary operators: clang::BO_Cmp"); | 1410 | emit_warning(c, stmt->getLocStart(), "TODO handle more C binary operators: clang::BO_Cmp"); |
| 1409 | return nullptr; | 1411 | return nullptr; |
| 1410 | case clang::BO_Mul: | 1412 | case clang::BO_Mul: { |
| 1411 | return trans_create_bin_op(c, scope, stmt->getLHS(), | 1413 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), |
| 1412 | qual_type_has_wrapping_overflow(c, stmt->getType()) ? BinOpTypeMultWrap : BinOpTypeMult, | 1414 | qual_type_has_wrapping_overflow(c, stmt->getType()) ? BinOpTypeMultWrap : BinOpTypeMult, |
| 1413 | stmt->getRHS()); | 1415 | stmt->getRHS()); |
| | 1416 | return maybe_suppress_result(c, result_used, node); |
| | 1417 | } |
| 1414 | case clang::BO_Div: | 1418 | case clang::BO_Div: |
| 1415 | if (qual_type_has_wrapping_overflow(c, stmt->getType())) { | 1419 | if (qual_type_has_wrapping_overflow(c, stmt->getType())) { |
| 1416 | // unsigned/float division uses the operator | 1420 | // unsigned/float division uses the operator |
| 1417 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeDiv, stmt->getRHS()); | 1421 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeDiv, stmt->getRHS()); |
| | 1422 | return maybe_suppress_result(c, result_used, node); |
| 1418 | } else { | 1423 | } else { |
| 1419 | // signed integer division uses @divTrunc | 1424 | // signed integer division uses @divTrunc |
| 1420 | AstNode *fn_call = trans_create_node_builtin_fn_call_str(c, "divTrunc"); | 1425 | AstNode *fn_call = trans_create_node_builtin_fn_call_str(c, "divTrunc"); |
| ... | @@ -1424,12 +1429,13 @@ static AstNode *trans_binary_operator(Context *c, ResultUsed result_used, TransS | ... | @@ -1424,12 +1429,13 @@ static AstNode *trans_binary_operator(Context *c, ResultUsed result_used, TransS |
| 1424 | AstNode *rhs = trans_expr(c, ResultUsedYes, scope, stmt->getRHS(), TransLValue); | 1429 | AstNode *rhs = trans_expr(c, ResultUsedYes, scope, stmt->getRHS(), TransLValue); |
| 1425 | if (rhs == nullptr) return nullptr; | 1430 | if (rhs == nullptr) return nullptr; |
| 1426 | fn_call->data.fn_call_expr.params.append(rhs); | 1431 | fn_call->data.fn_call_expr.params.append(rhs); |
| 1427 | return fn_call; | 1432 | return maybe_suppress_result(c, result_used, fn_call); |
| 1428 | } | 1433 | } |
| 1429 | case clang::BO_Rem: | 1434 | case clang::BO_Rem: |
| 1430 | if (qual_type_has_wrapping_overflow(c, stmt->getType())) { | 1435 | if (qual_type_has_wrapping_overflow(c, stmt->getType())) { |
| 1431 | // unsigned/float division uses the operator | 1436 | // unsigned/float division uses the operator |
| 1432 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeMod, stmt->getRHS()); | 1437 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeMod, stmt->getRHS()); |
| | 1438 | return maybe_suppress_result(c, result_used, node); |
| 1433 | } else { | 1439 | } else { |
| 1434 | // signed integer division uses @rem | 1440 | // signed integer division uses @rem |
| 1435 | AstNode *fn_call = trans_create_node_builtin_fn_call_str(c, "rem"); | 1441 | AstNode *fn_call = trans_create_node_builtin_fn_call_str(c, "rem"); |
| ... | @@ -1439,42 +1445,72 @@ static AstNode *trans_binary_operator(Context *c, ResultUsed result_used, TransS | ... | @@ -1439,42 +1445,72 @@ static AstNode *trans_binary_operator(Context *c, ResultUsed result_used, TransS |
| 1439 | AstNode *rhs = trans_expr(c, ResultUsedYes, scope, stmt->getRHS(), TransLValue); | 1445 | AstNode *rhs = trans_expr(c, ResultUsedYes, scope, stmt->getRHS(), TransLValue); |
| 1440 | if (rhs == nullptr) return nullptr; | 1446 | if (rhs == nullptr) return nullptr; |
| 1441 | fn_call->data.fn_call_expr.params.append(rhs); | 1447 | fn_call->data.fn_call_expr.params.append(rhs); |
| 1442 | return fn_call; | 1448 | return maybe_suppress_result(c, result_used, fn_call); |
| 1443 | } | 1449 | } |
| 1444 | case clang::BO_Add: | 1450 | case clang::BO_Add: { |
| 1445 | return trans_create_bin_op(c, scope, stmt->getLHS(), | 1451 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), |
| 1446 | qual_type_has_wrapping_overflow(c, stmt->getType()) ? BinOpTypeAddWrap : BinOpTypeAdd, | 1452 | qual_type_has_wrapping_overflow(c, stmt->getType()) ? BinOpTypeAddWrap : BinOpTypeAdd, |
| 1447 | stmt->getRHS()); | 1453 | stmt->getRHS()); |
| 1448 | case clang::BO_Sub: | 1454 | return maybe_suppress_result(c, result_used, node); |
| 1449 | return trans_create_bin_op(c, scope, stmt->getLHS(), | 1455 | } |
| | 1456 | case clang::BO_Sub: { |
| | 1457 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), |
| 1450 | qual_type_has_wrapping_overflow(c, stmt->getType()) ? BinOpTypeSubWrap : BinOpTypeSub, | 1458 | qual_type_has_wrapping_overflow(c, stmt->getType()) ? BinOpTypeSubWrap : BinOpTypeSub, |
| 1451 | stmt->getRHS()); | 1459 | stmt->getRHS()); |
| 1452 | case clang::BO_Shl: | 1460 | return maybe_suppress_result(c, result_used, node); |
| 1453 | return trans_create_shift_op(c, scope, stmt->getType(), stmt->getLHS(), BinOpTypeBitShiftLeft, stmt->getRHS()); | 1461 | } |
| 1454 | case clang::BO_Shr: | 1462 | case clang::BO_Shl: { |
| 1455 | return trans_create_shift_op(c, scope, stmt->getType(), stmt->getLHS(), BinOpTypeBitShiftRight, stmt->getRHS()); | 1463 | AstNode *node = trans_create_shift_op(c, scope, stmt->getType(), stmt->getLHS(), BinOpTypeBitShiftLeft, stmt->getRHS()); |
| 1456 | case clang::BO_LT: | 1464 | return maybe_suppress_result(c, result_used, node); |
| 1457 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpLessThan, stmt->getRHS()); | 1465 | } |
| 1458 | case clang::BO_GT: | 1466 | case clang::BO_Shr: { |
| 1459 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpGreaterThan, stmt->getRHS()); | 1467 | AstNode *node = trans_create_shift_op(c, scope, stmt->getType(), stmt->getLHS(), BinOpTypeBitShiftRight, stmt->getRHS()); |
| 1460 | case clang::BO_LE: | 1468 | return maybe_suppress_result(c, result_used, node); |
| 1461 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpLessOrEq, stmt->getRHS()); | 1469 | } |
| 1462 | case clang::BO_GE: | 1470 | case clang::BO_LT: { |
| 1463 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpGreaterOrEq, stmt->getRHS()); | 1471 | AstNode *node =trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpLessThan, stmt->getRHS()); |
| 1464 | case clang::BO_EQ: | 1472 | return maybe_suppress_result(c, result_used, node); |
| 1465 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpEq, stmt->getRHS()); | 1473 | } |
| 1466 | case clang::BO_NE: | 1474 | case clang::BO_GT: { |
| 1467 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpNotEq, stmt->getRHS()); | 1475 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpGreaterThan, stmt->getRHS()); |
| 1468 | case clang::BO_And: | 1476 | return maybe_suppress_result(c, result_used, node); |
| 1469 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeBinAnd, stmt->getRHS()); | 1477 | } |
| 1470 | case clang::BO_Xor: | 1478 | case clang::BO_LE: { |
| 1471 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeBinXor, stmt->getRHS()); | 1479 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpLessOrEq, stmt->getRHS()); |
| 1472 | case clang::BO_Or: | 1480 | return maybe_suppress_result(c, result_used, node); |
| 1473 | return trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeBinOr, stmt->getRHS()); | 1481 | } |
| 1474 | case clang::BO_LAnd: | 1482 | case clang::BO_GE: { |
| 1475 | return trans_create_bool_bin_op(c, scope, stmt->getLHS(), BinOpTypeBoolAnd, stmt->getRHS()); | 1483 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpGreaterOrEq, stmt->getRHS()); |
| 1476 | case clang::BO_LOr: | 1484 | return maybe_suppress_result(c, result_used, node); |
| 1477 | return trans_create_bool_bin_op(c, scope, stmt->getLHS(), BinOpTypeBoolOr, stmt->getRHS()); | 1485 | } |
| | 1486 | case clang::BO_EQ: { |
| | 1487 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpEq, stmt->getRHS()); |
| | 1488 | return maybe_suppress_result(c, result_used, node); |
| | 1489 | } |
| | 1490 | case clang::BO_NE: { |
| | 1491 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeCmpNotEq, stmt->getRHS()); |
| | 1492 | return maybe_suppress_result(c, result_used, node); |
| | 1493 | } |
| | 1494 | case clang::BO_And: { |
| | 1495 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeBinAnd, stmt->getRHS()); |
| | 1496 | return maybe_suppress_result(c, result_used, node); |
| | 1497 | } |
| | 1498 | case clang::BO_Xor: { |
| | 1499 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeBinXor, stmt->getRHS()); |
| | 1500 | return maybe_suppress_result(c, result_used, node); |
| | 1501 | } |
| | 1502 | case clang::BO_Or: { |
| | 1503 | AstNode *node = trans_create_bin_op(c, scope, stmt->getLHS(), BinOpTypeBinOr, stmt->getRHS()); |
| | 1504 | return maybe_suppress_result(c, result_used, node); |
| | 1505 | } |
| | 1506 | case clang::BO_LAnd: { |
| | 1507 | AstNode *node = trans_create_bool_bin_op(c, scope, stmt->getLHS(), BinOpTypeBoolAnd, stmt->getRHS()); |
| | 1508 | return maybe_suppress_result(c, result_used, node); |
| | 1509 | } |
| | 1510 | case clang::BO_LOr: { |
| | 1511 | AstNode *node = trans_create_bool_bin_op(c, scope, stmt->getLHS(), BinOpTypeBoolOr, stmt->getRHS()); |
| | 1512 | return maybe_suppress_result(c, result_used, node); |
| | 1513 | } |
| 1478 | case clang::BO_Assign: | 1514 | case clang::BO_Assign: |
| 1479 | return trans_create_assign(c, result_used, scope, stmt->getLHS(), stmt->getRHS()); | 1515 | return trans_create_assign(c, result_used, scope, stmt->getLHS(), stmt->getRHS()); |
| 1480 | case clang::BO_Comma: | 1516 | case clang::BO_Comma: |
| ... | @@ -1486,13 +1522,15 @@ static AstNode *trans_binary_operator(Context *c, ResultUsed result_used, TransS | ... | @@ -1486,13 +1522,15 @@ static AstNode *trans_binary_operator(Context *c, ResultUsed result_used, TransS |
| 1486 | AstNode *lhs = trans_expr(c, ResultUsedNo, &scope_block->base, stmt->getLHS(), TransRValue); | 1522 | AstNode *lhs = trans_expr(c, ResultUsedNo, &scope_block->base, stmt->getLHS(), TransRValue); |
| 1487 | if (lhs == nullptr) | 1523 | if (lhs == nullptr) |
| 1488 | return nullptr; | 1524 | return nullptr; |
| 1489 | scope_block->node->data.block.statements.append(maybe_suppress_result(c, ResultUsedNo, lhs)); | 1525 | scope_block->node->data.block.statements.append(lhs); |
| 1490 | | 1526 | |
| 1491 | AstNode *rhs = trans_expr(c, result_used, &scope_block->base, stmt->getRHS(), TransRValue); | 1527 | AstNode *rhs = trans_expr(c, ResultUsedYes, &scope_block->base, stmt->getRHS(), TransRValue); |
| 1492 | if (rhs == nullptr) | 1528 | if (rhs == nullptr) |
| 1493 | return nullptr; | 1529 | return nullptr; |
| 1494 | scope_block->node->data.block.statements.append(trans_create_node_break(c, label_name, rhs)); | 1530 | |
| 1495 | return scope_block->node; | 1531 | rhs = trans_create_node_break(c, label_name, rhs); |
| | 1532 | scope_block->node->data.block.statements.append(rhs); |
| | 1533 | return maybe_suppress_result(c, result_used, scope_block->node); |
| 1496 | } | 1534 | } |
| 1497 | case clang::BO_MulAssign: | 1535 | case clang::BO_MulAssign: |
| 1498 | case clang::BO_DivAssign: | 1536 | case clang::BO_DivAssign: |
| ... | @@ -1718,7 +1756,7 @@ static AstNode *trans_compound_assign_operator(Context *c, ResultUsed result_use | ... | @@ -1718,7 +1756,7 @@ static AstNode *trans_compound_assign_operator(Context *c, ResultUsed result_use |
| 1718 | zig_unreachable(); | 1756 | zig_unreachable(); |
| 1719 | } | 1757 | } |
| 1720 | | 1758 | |
| 1721 | static AstNode *trans_implicit_cast_expr(Context *c, TransScope *scope, const clang::ImplicitCastExpr *stmt) { | 1759 | static AstNode *trans_implicit_cast_expr(Context *c, ResultUsed result_used, TransScope *scope, const clang::ImplicitCastExpr *stmt) { |
| 1722 | switch (stmt->getCastKind()) { | 1760 | switch (stmt->getCastKind()) { |
| 1723 | case clang::CK_LValueToRValue: | 1761 | case clang::CK_LValueToRValue: |
| 1724 | return trans_expr(c, ResultUsedYes, scope, stmt->getSubExpr(), TransRValue); | 1762 | return trans_expr(c, ResultUsedYes, scope, stmt->getSubExpr(), TransRValue); |
| ... | @@ -1727,8 +1765,9 @@ static AstNode *trans_implicit_cast_expr(Context *c, TransScope *scope, const cl | ... | @@ -1727,8 +1765,9 @@ static AstNode *trans_implicit_cast_expr(Context *c, TransScope *scope, const cl |
| 1727 | AstNode *target_node = trans_expr(c, ResultUsedYes, scope, stmt->getSubExpr(), TransRValue); | 1765 | AstNode *target_node = trans_expr(c, ResultUsedYes, scope, stmt->getSubExpr(), TransRValue); |
| 1728 | if (target_node == nullptr) | 1766 | if (target_node == nullptr) |
| 1729 | return nullptr; | 1767 | return nullptr; |
| 1730 | return trans_c_cast(c, stmt->getExprLoc(), stmt->getType(), | 1768 | AstNode *node = trans_c_cast(c, stmt->getExprLoc(), stmt->getType(), |
| 1731 | stmt->getSubExpr()->getType(), target_node); | 1769 | stmt->getSubExpr()->getType(), target_node); |
| | 1770 | return maybe_suppress_result(c, result_used, node); |
| 1732 | } | 1771 | } |
| 1733 | case clang::CK_FunctionToPointerDecay: | 1772 | case clang::CK_FunctionToPointerDecay: |
| 1734 | case clang::CK_ArrayToPointerDecay: | 1773 | case clang::CK_ArrayToPointerDecay: |
| ... | @@ -1736,7 +1775,7 @@ static AstNode *trans_implicit_cast_expr(Context *c, TransScope *scope, const cl | ... | @@ -1736,7 +1775,7 @@ static AstNode *trans_implicit_cast_expr(Context *c, TransScope *scope, const cl |
| 1736 | AstNode *target_node = trans_expr(c, ResultUsedYes, scope, stmt->getSubExpr(), TransRValue); | 1775 | AstNode *target_node = trans_expr(c, ResultUsedYes, scope, stmt->getSubExpr(), TransRValue); |
| 1737 | if (target_node == nullptr) | 1776 | if (target_node == nullptr) |
| 1738 | return nullptr; | 1777 | return nullptr; |
| 1739 | return target_node; | 1778 | return maybe_suppress_result(c, result_used, target_node); |
| 1740 | } | 1779 | } |
| 1741 | case clang::CK_BitCast: | 1780 | case clang::CK_BitCast: |
| 1742 | { | 1781 | { |
| ... | @@ -1753,7 +1792,7 @@ static AstNode *trans_implicit_cast_expr(Context *c, TransScope *scope, const cl | ... | @@ -1753,7 +1792,7 @@ static AstNode *trans_implicit_cast_expr(Context *c, TransScope *scope, const cl |
| 1753 | AstNode *node = trans_create_node_builtin_fn_call_str(c, "ptrCast"); | 1792 | AstNode *node = trans_create_node_builtin_fn_call_str(c, "ptrCast"); |
| 1754 | node->data.fn_call_expr.params.append(dest_type_node); | 1793 | node->data.fn_call_expr.params.append(dest_type_node); |
| 1755 | node->data.fn_call_expr.params.append(target_node); | 1794 | node->data.fn_call_expr.params.append(target_node); |
| 1756 | return node; | 1795 | return maybe_suppress_result(c, result_used, node); |
| 1757 | } | 1796 | } |
| 1758 | case clang::CK_NullToPointer: | 1797 | case clang::CK_NullToPointer: |
| 1759 | return trans_create_node_unsigned(c, 0); | 1798 | return trans_create_node_unsigned(c, 0); |
| ... | @@ -2746,7 +2785,9 @@ static AstNode *trans_call_expr(Context *c, ResultUsed result_used, TransScope * | ... | @@ -2746,7 +2785,9 @@ static AstNode *trans_call_expr(Context *c, ResultUsed result_used, TransScope * |
| 2746 | return node; | 2785 | return node; |
| 2747 | } | 2786 | } |
| 2748 | | 2787 | |
| 2749 | static AstNode *trans_member_expr(Context *c, TransScope *scope, const clang::MemberExpr *stmt) { | 2788 | static AstNode *trans_member_expr(Context *c, ResultUsed result_used, TransScope *scope, |
| | 2789 | const clang::MemberExpr *stmt) |
| | 2790 | { |
| 2750 | AstNode *container_node = trans_expr(c, ResultUsedYes, scope, stmt->getBase(), TransRValue); | 2791 | AstNode *container_node = trans_expr(c, ResultUsedYes, scope, stmt->getBase(), TransRValue); |
| 2751 | if (container_node == nullptr) | 2792 | if (container_node == nullptr) |
| 2752 | return nullptr; | 2793 | return nullptr; |
| ... | @@ -2758,10 +2799,10 @@ static AstNode *trans_member_expr(Context *c, TransScope *scope, const clang::Me | ... | @@ -2758,10 +2799,10 @@ static AstNode *trans_member_expr(Context *c, TransScope *scope, const clang::Me |
| 2758 | const char *name = decl_name(stmt->getMemberDecl()); | 2799 | const char *name = decl_name(stmt->getMemberDecl()); |
| 2759 | | 2800 | |
| 2760 | AstNode *node = trans_create_node_field_access_str(c, container_node, name); | 2801 | AstNode *node = trans_create_node_field_access_str(c, container_node, name); |
| 2761 | return node; | 2802 | return maybe_suppress_result(c, result_used, node); |
| 2762 | } | 2803 | } |
| 2763 | | 2804 | |
| 2764 | static AstNode *trans_array_subscript_expr(Context *c, TransScope *scope, const clang::ArraySubscriptExpr *stmt) { | 2805 | static AstNode *trans_array_subscript_expr(Context *c, ResultUsed result_used, TransScope *scope, const clang::ArraySubscriptExpr *stmt) { |
| 2765 | AstNode *container_node = trans_expr(c, ResultUsedYes, scope, stmt->getBase(), TransRValue); | 2806 | AstNode *container_node = trans_expr(c, ResultUsedYes, scope, stmt->getBase(), TransRValue); |
| 2766 | if (container_node == nullptr) | 2807 | if (container_node == nullptr) |
| 2767 | return nullptr; | 2808 | return nullptr; |
| ... | @@ -2774,13 +2815,13 @@ static AstNode *trans_array_subscript_expr(Context *c, TransScope *scope, const | ... | @@ -2774,13 +2815,13 @@ static AstNode *trans_array_subscript_expr(Context *c, TransScope *scope, const |
| 2774 | AstNode *node = trans_create_node(c, NodeTypeArrayAccessExpr); | 2815 | AstNode *node = trans_create_node(c, NodeTypeArrayAccessExpr); |
| 2775 | node->data.array_access_expr.array_ref_expr = container_node; | 2816 | node->data.array_access_expr.array_ref_expr = container_node; |
| 2776 | node->data.array_access_expr.subscript = idx_node; | 2817 | node->data.array_access_expr.subscript = idx_node; |
| 2777 | return node; | 2818 | return maybe_suppress_result(c, result_used, node); |
| 2778 | } | 2819 | } |
| 2779 | | 2820 | |
| 2780 | static AstNode *trans_c_style_cast_expr(Context *c, ResultUsed result_used, TransScope *scope, | 2821 | static AstNode *trans_c_style_cast_expr(Context *c, ResultUsed result_used, TransScope *scope, |
| 2781 | const clang::CStyleCastExpr *stmt, TransLRValue lrvalue) | 2822 | const clang::CStyleCastExpr *stmt, TransLRValue lrvalue) |
| 2782 | { | 2823 | { |
| 2783 | AstNode *sub_expr_node = trans_expr(c, result_used, scope, stmt->getSubExpr(), lrvalue); | 2824 | AstNode *sub_expr_node = trans_expr(c, ResultUsedYes, scope, stmt->getSubExpr(), lrvalue); |
| 2784 | if (sub_expr_node == nullptr) | 2825 | if (sub_expr_node == nullptr) |
| 2785 | return nullptr; | 2826 | return nullptr; |
| 2786 | | 2827 | |
| ... | @@ -2791,8 +2832,8 @@ static AstNode *trans_c_style_cast_expr(Context *c, ResultUsed result_used, Tran | ... | @@ -2791,8 +2832,8 @@ static AstNode *trans_c_style_cast_expr(Context *c, ResultUsed result_used, Tran |
| 2791 | return maybe_suppress_result(c, result_used, cast); | 2832 | return maybe_suppress_result(c, result_used, cast); |
| 2792 | } | 2833 | } |
| 2793 | | 2834 | |
| 2794 | static AstNode *trans_unary_expr_or_type_trait_expr(Context *c, TransScope *scope, | 2835 | static AstNode *trans_unary_expr_or_type_trait_expr(Context *c, ResultUsed result_used, |
| 2795 | const clang::UnaryExprOrTypeTraitExpr *stmt) | 2836 | TransScope *scope, const clang::UnaryExprOrTypeTraitExpr *stmt) |
| 2796 | { | 2837 | { |
| 2797 | AstNode *type_node = trans_qual_type(c, stmt->getTypeOfArgument(), stmt->getLocStart()); | 2838 | AstNode *type_node = trans_qual_type(c, stmt->getTypeOfArgument(), stmt->getLocStart()); |
| 2798 | if (type_node == nullptr) | 2839 | if (type_node == nullptr) |
| ... | @@ -2800,7 +2841,7 @@ static AstNode *trans_unary_expr_or_type_trait_expr(Context *c, TransScope *scop | ... | @@ -2800,7 +2841,7 @@ static AstNode *trans_unary_expr_or_type_trait_expr(Context *c, TransScope *scop |
| 2800 | | 2841 | |
| 2801 | AstNode *node = trans_create_node_builtin_fn_call_str(c, "sizeOf"); | 2842 | AstNode *node = trans_create_node_builtin_fn_call_str(c, "sizeOf"); |
| 2802 | node->data.fn_call_expr.params.append(type_node); | 2843 | node->data.fn_call_expr.params.append(type_node); |
| 2803 | return node; | 2844 | return maybe_suppress_result(c, result_used, node); |
| 2804 | } | 2845 | } |
| 2805 | | 2846 | |
| 2806 | static AstNode *trans_do_loop(Context *c, TransScope *parent_scope, const clang::DoStmt *stmt) { | 2847 | static AstNode *trans_do_loop(Context *c, TransScope *parent_scope, const clang::DoStmt *stmt) { |
| ... | @@ -3078,11 +3119,13 @@ static int trans_switch_default(Context *c, TransScope *parent_scope, const clan | ... | @@ -3078,11 +3119,13 @@ static int trans_switch_default(Context *c, TransScope *parent_scope, const clan |
| 3078 | return ErrorNone; | 3119 | return ErrorNone; |
| 3079 | } | 3120 | } |
| 3080 | | 3121 | |
| 3081 | static AstNode *trans_string_literal(Context *c, TransScope *scope, const clang::StringLiteral *stmt) { | 3122 | static AstNode *trans_string_literal(Context *c, ResultUsed result_used, TransScope *scope, const clang::StringLiteral *stmt) { |
| 3082 | switch (stmt->getKind()) { | 3123 | switch (stmt->getKind()) { |
| 3083 | case clang::StringLiteral::Ascii: | 3124 | case clang::StringLiteral::Ascii: |
| 3084 | case clang::StringLiteral::UTF8: | 3125 | case clang::StringLiteral::UTF8: { |
| 3085 | return trans_create_node_str_lit_c(c, string_ref_to_buf(stmt->getString())); | 3126 | AstNode *node = trans_create_node_str_lit_c(c, string_ref_to_buf(stmt->getString())); |
| | 3127 | return maybe_suppress_result(c, result_used, node); |
| | 3128 | } |
| 3086 | case clang::StringLiteral::UTF16: | 3129 | case clang::StringLiteral::UTF16: |
| 3087 | emit_warning(c, stmt->getLocStart(), "TODO support UTF16 string literals"); | 3130 | emit_warning(c, stmt->getLocStart(), "TODO support UTF16 string literals"); |
| 3088 | return nullptr; | 3131 | return nullptr; |
| ... | @@ -3114,8 +3157,10 @@ static AstNode *trans_continue_stmt(Context *c, TransScope *scope, const clang:: | ... | @@ -3114,8 +3157,10 @@ static AstNode *trans_continue_stmt(Context *c, TransScope *scope, const clang:: |
| 3114 | return trans_create_node(c, NodeTypeContinue); | 3157 | return trans_create_node(c, NodeTypeContinue); |
| 3115 | } | 3158 | } |
| 3116 | | 3159 | |
| 3117 | static AstNode *trans_predefined_expr(Context *c, TransScope *scope, const clang::PredefinedExpr *expr) { | 3160 | static AstNode *trans_predefined_expr(Context *c, ResultUsed result_used, TransScope *scope, |
| 3118 | return trans_string_literal(c, scope, expr->getFunctionName()); | 3161 | const clang::PredefinedExpr *expr) |
| | 3162 | { |
| | 3163 | return trans_string_literal(c, result_used, scope, expr->getFunctionName()); |
| 3119 | } | 3164 | } |
| 3120 | | 3165 | |
| 3121 | static int wrap_stmt(AstNode **out_node, TransScope **out_scope, TransScope *in_scope, AstNode *result_node) { | 3166 | static int wrap_stmt(AstNode **out_node, TransScope **out_scope, TransScope *in_scope, AstNode *result_node) { |
| ... | @@ -3142,7 +3187,7 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st | ... | @@ -3142,7 +3187,7 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st |
| 3142 | trans_compound_stmt(c, scope, (const clang::CompoundStmt *)stmt, out_node_scope)); | 3187 | trans_compound_stmt(c, scope, (const clang::CompoundStmt *)stmt, out_node_scope)); |
| 3143 | case clang::Stmt::IntegerLiteralClass: | 3188 | case clang::Stmt::IntegerLiteralClass: |
| 3144 | return wrap_stmt(out_node, out_child_scope, scope, | 3189 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3145 | trans_integer_literal(c, (const clang::IntegerLiteral *)stmt)); | 3190 | trans_integer_literal(c, result_used, (const clang::IntegerLiteral *)stmt)); |
| 3146 | case clang::Stmt::ConditionalOperatorClass: | 3191 | case clang::Stmt::ConditionalOperatorClass: |
| 3147 | return wrap_stmt(out_node, out_child_scope, scope, | 3192 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3148 | trans_conditional_operator(c, result_used, scope, (const clang::ConditionalOperator *)stmt)); | 3193 | trans_conditional_operator(c, result_used, scope, (const clang::ConditionalOperator *)stmt)); |
| ... | @@ -3154,7 +3199,7 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st | ... | @@ -3154,7 +3199,7 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st |
| 3154 | trans_compound_assign_operator(c, result_used, scope, (const clang::CompoundAssignOperator *)stmt)); | 3199 | trans_compound_assign_operator(c, result_used, scope, (const clang::CompoundAssignOperator *)stmt)); |
| 3155 | case clang::Stmt::ImplicitCastExprClass: | 3200 | case clang::Stmt::ImplicitCastExprClass: |
| 3156 | return wrap_stmt(out_node, out_child_scope, scope, | 3201 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3157 | trans_implicit_cast_expr(c, scope, (const clang::ImplicitCastExpr *)stmt)); | 3202 | trans_implicit_cast_expr(c, result_used, scope, (const clang::ImplicitCastExpr *)stmt)); |
| 3158 | case clang::Stmt::DeclRefExprClass: | 3203 | case clang::Stmt::DeclRefExprClass: |
| 3159 | return wrap_stmt(out_node, out_child_scope, scope, | 3204 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3160 | trans_decl_ref_expr(c, scope, (const clang::DeclRefExpr *)stmt, lrvalue)); | 3205 | trans_decl_ref_expr(c, scope, (const clang::DeclRefExpr *)stmt, lrvalue)); |
| ... | @@ -3190,23 +3235,23 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st | ... | @@ -3190,23 +3235,23 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st |
| 3190 | return ErrorNone; | 3235 | return ErrorNone; |
| 3191 | case clang::Stmt::MemberExprClass: | 3236 | case clang::Stmt::MemberExprClass: |
| 3192 | return wrap_stmt(out_node, out_child_scope, scope, | 3237 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3193 | trans_member_expr(c, scope, (const clang::MemberExpr *)stmt)); | 3238 | trans_member_expr(c, result_used, scope, (const clang::MemberExpr *)stmt)); |
| 3194 | case clang::Stmt::ArraySubscriptExprClass: | 3239 | case clang::Stmt::ArraySubscriptExprClass: |
| 3195 | return wrap_stmt(out_node, out_child_scope, scope, | 3240 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3196 | trans_array_subscript_expr(c, scope, (const clang::ArraySubscriptExpr *)stmt)); | 3241 | trans_array_subscript_expr(c, result_used, scope, (const clang::ArraySubscriptExpr *)stmt)); |
| 3197 | case clang::Stmt::CStyleCastExprClass: | 3242 | case clang::Stmt::CStyleCastExprClass: |
| 3198 | return wrap_stmt(out_node, out_child_scope, scope, | 3243 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3199 | trans_c_style_cast_expr(c, result_used, scope, (const clang::CStyleCastExpr *)stmt, lrvalue)); | 3244 | trans_c_style_cast_expr(c, result_used, scope, (const clang::CStyleCastExpr *)stmt, lrvalue)); |
| 3200 | case clang::Stmt::UnaryExprOrTypeTraitExprClass: | 3245 | case clang::Stmt::UnaryExprOrTypeTraitExprClass: |
| 3201 | return wrap_stmt(out_node, out_child_scope, scope, | 3246 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3202 | trans_unary_expr_or_type_trait_expr(c, scope, (const clang::UnaryExprOrTypeTraitExpr *)stmt)); | 3247 | trans_unary_expr_or_type_trait_expr(c, result_used, scope, (const clang::UnaryExprOrTypeTraitExpr *)stmt)); |
| 3203 | case clang::Stmt::ForStmtClass: { | 3248 | case clang::Stmt::ForStmtClass: { |
| 3204 | AstNode *node = trans_for_loop(c, scope, (const clang::ForStmt *)stmt); | 3249 | AstNode *node = trans_for_loop(c, scope, (const clang::ForStmt *)stmt); |
| 3205 | return wrap_stmt(out_node, out_child_scope, scope, node); | 3250 | return wrap_stmt(out_node, out_child_scope, scope, node); |
| 3206 | } | 3251 | } |
| 3207 | case clang::Stmt::StringLiteralClass: | 3252 | case clang::Stmt::StringLiteralClass: |
| 3208 | return wrap_stmt(out_node, out_child_scope, scope, | 3253 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3209 | trans_string_literal(c, scope, (const clang::StringLiteral *)stmt)); | 3254 | trans_string_literal(c, result_used, scope, (const clang::StringLiteral *)stmt)); |
| 3210 | case clang::Stmt::BreakStmtClass: | 3255 | case clang::Stmt::BreakStmtClass: |
| 3211 | return wrap_stmt(out_node, out_child_scope, scope, | 3256 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3212 | trans_break_stmt(c, scope, (const clang::BreakStmt *)stmt)); | 3257 | trans_break_stmt(c, scope, (const clang::BreakStmt *)stmt)); |
| ... | @@ -3513,7 +3558,7 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st | ... | @@ -3513,7 +3558,7 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st |
| 3513 | return ErrorUnexpected; | 3558 | return ErrorUnexpected; |
| 3514 | case clang::Stmt::PredefinedExprClass: | 3559 | case clang::Stmt::PredefinedExprClass: |
| 3515 | return wrap_stmt(out_node, out_child_scope, scope, | 3560 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3516 | trans_predefined_expr(c, scope, (const clang::PredefinedExpr *)stmt)); | 3561 | trans_predefined_expr(c, result_used, scope, (const clang::PredefinedExpr *)stmt)); |
| 3517 | case clang::Stmt::PseudoObjectExprClass: | 3562 | case clang::Stmt::PseudoObjectExprClass: |
| 3518 | emit_warning(c, stmt->getLocStart(), "TODO handle C PseudoObjectExprClass"); | 3563 | emit_warning(c, stmt->getLocStart(), "TODO handle C PseudoObjectExprClass"); |
| 3519 | return ErrorUnexpected; | 3564 | return ErrorUnexpected; |
| ... | @@ -3525,7 +3570,7 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st | ... | @@ -3525,7 +3570,7 @@ static int trans_stmt_extra(Context *c, TransScope *scope, const clang::Stmt *st |
| 3525 | return ErrorUnexpected; | 3570 | return ErrorUnexpected; |
| 3526 | case clang::Stmt::StmtExprClass: | 3571 | case clang::Stmt::StmtExprClass: |
| 3527 | return wrap_stmt(out_node, out_child_scope, scope, | 3572 | return wrap_stmt(out_node, out_child_scope, scope, |
| 3528 | trans_stmt_expr(c, scope, (const clang::StmtExpr *)stmt, out_node_scope)); | 3573 | trans_stmt_expr(c, result_used, scope, (const clang::StmtExpr *)stmt, out_node_scope)); |
| 3529 | case clang::Stmt::SubstNonTypeTemplateParmExprClass: | 3574 | case clang::Stmt::SubstNonTypeTemplateParmExprClass: |
| 3530 | emit_warning(c, stmt->getLocStart(), "TODO handle C SubstNonTypeTemplateParmExprClass"); | 3575 | emit_warning(c, stmt->getLocStart(), "TODO handle C SubstNonTypeTemplateParmExprClass"); |
| 3531 | return ErrorUnexpected; | 3576 | return ErrorUnexpected; |