|
1 | 1 | # SPDX-FileCopyrightText: Copyright (c) <2025> NVIDIA CORPORATION & AFFILIATES. All rights reserved. |
2 | 2 | # |
3 | 3 | # SPDX-License-Identifier: Apache-2.0 |
| 4 | +import builtins |
4 | 5 | import enum |
5 | 6 | import math |
6 | 7 | import operator |
|
23 | 24 | add_operation, Builder, |
24 | 25 | enter_nested_block, nested_block, PhiState, LoopVarState, |
25 | 26 | TupleValue, make_aggregate, RangeValue, BoundMethodValue, ArrayValue, ConstantState, |
26 | | - ListValue, TiledViewValue, ClosureValue, MemoryEffect, attribute, operand, BlockRestriction |
| 27 | + ListValue, TiledViewValue, ClosureValue, MemoryEffect, attribute, operand, |
| 28 | + BlockRestriction, FormattedStringValue, |
27 | 29 | ) |
28 | 30 | from .type import PointerTy |
29 | 31 | from . import hir |
|
57 | 59 | PartitionViewTy, TupleTy, TileTy, NoneType, BoundMethodTy, ArrayTy, |
58 | 60 | ListTy, make_tile_ty, SliceType, DTypeConstructor, RangeIterType, Type, |
59 | 61 | NONE, ModuleTy, TypeTy, LooselyTypedScalar, DTypeSpec, StringTy, InvalidType, |
60 | | - array_size_type, ClosureTy, LiveCapturedScope, TokenTy, TiledViewTy |
| 62 | + array_size_type, ClosureTy, LiveCapturedScope, TokenTy, TiledViewTy, FormattedStringTy, |
| 63 | + StringFormat, FormattedPiece, |
61 | 64 | ) |
62 | 65 | from cuda.tile._datatype import ( |
63 | 66 | DType, is_integral, is_float, is_signed, is_boolean, is_restricted_float, |
@@ -1318,6 +1321,39 @@ def build_tuple(items: tuple[Var, ...]) -> Var: |
1318 | 1321 | return res |
1319 | 1322 |
|
1320 | 1323 |
|
| 1324 | +@impl(hir.build_formatted_string) |
| 1325 | +def build_formatted_string_impl(format: StringFormat, values: tuple[Var, ...]) -> Var: |
| 1326 | + new_pieces = [] |
| 1327 | + new_values = [] |
| 1328 | + for piece in format.pieces: |
| 1329 | + if isinstance(piece, str): |
| 1330 | + new_pieces.append(piece) |
| 1331 | + else: |
| 1332 | + val_var = values[piece.value_idx] |
| 1333 | + val_ty = val_var.get_type() |
| 1334 | + if isinstance(val_ty, FormattedStringTy): |
| 1335 | + if piece.format_spec is not None: |
| 1336 | + raise TileTypeError( |
| 1337 | + "f-string: cannot apply format spec to a formatted string value", |
| 1338 | + val_var.loc) |
| 1339 | + inner_val = val_var.get_aggregate() |
| 1340 | + assert isinstance(inner_val, FormattedStringValue) |
| 1341 | + offset = len(new_values) |
| 1342 | + for inner_piece in val_ty.format.pieces: |
| 1343 | + if isinstance(inner_piece, str): |
| 1344 | + new_pieces.append(inner_piece) |
| 1345 | + else: |
| 1346 | + new_pieces.append(FormattedPiece( |
| 1347 | + offset + inner_piece.value_idx, inner_piece.format_spec)) |
| 1348 | + new_values.extend(inner_val.values) |
| 1349 | + else: |
| 1350 | + new_pieces.append(FormattedPiece(len(new_values), piece.format_spec)) |
| 1351 | + new_values.append(val_var) |
| 1352 | + new_fmt = StringFormat(tuple(new_pieces)) |
| 1353 | + ty = FormattedStringTy(new_fmt, tuple(v.get_type() for v in new_values)) |
| 1354 | + return make_aggregate(FormattedStringValue(new_fmt, tuple(new_values)), ty) |
| 1355 | + |
| 1356 | + |
1321 | 1357 | @impl(hir.unpack) |
1322 | 1358 | def unpack_impl(iterable: Var, expected_len: Var) -> Var: |
1323 | 1359 | ty = iterable.get_type() |
@@ -3638,6 +3674,50 @@ def printf_impl(format: Var, args: Tuple[Var, ...]) -> None: |
3638 | 3674 | add_operation(TilePrintf, (), format=parsed_format, args=args) |
3639 | 3675 |
|
3640 | 3676 |
|
| 3677 | +@impl(ct.print) |
| 3678 | +@impl(builtins.print) |
| 3679 | +def print_impl(args: Tuple[Var, ...], sep: Var, end: Var) -> None: |
| 3680 | + sep_str = PrintfValidator.escape_str(require_constant_str(sep)) |
| 3681 | + end_str = PrintfValidator.escape_str(require_constant_str(end)) |
| 3682 | + |
| 3683 | + format_parts = [] |
| 3684 | + leaf_vars = [] |
| 3685 | + first = True |
| 3686 | + |
| 3687 | + for arg_var in args: |
| 3688 | + if not first: |
| 3689 | + format_parts.append(sep_str) |
| 3690 | + else: |
| 3691 | + first = False |
| 3692 | + |
| 3693 | + arg_ty = arg_var.get_type() |
| 3694 | + if isinstance(arg_ty, FormattedStringTy): |
| 3695 | + fmt_val = arg_var.get_aggregate() |
| 3696 | + assert isinstance(fmt_val, FormattedStringValue) |
| 3697 | + for piece in arg_ty.format.pieces: |
| 3698 | + if isinstance(piece, str): |
| 3699 | + format_parts.append(PrintfValidator.escape_str(piece)) |
| 3700 | + else: |
| 3701 | + value_ty = arg_ty.value_types[piece.value_idx] |
| 3702 | + dtype = get_dtype(value_ty) |
| 3703 | + if piece.format_spec is not None: |
| 3704 | + format_parts.append(PrintfValidator.apply_python_spec( |
| 3705 | + piece.format_spec, dtype)) |
| 3706 | + else: |
| 3707 | + format_parts.append(PrintfValidator.infer_format(dtype)) |
| 3708 | + leaf_vars.append(fmt_val.values[piece.value_idx]) |
| 3709 | + elif isinstance(arg_ty, StringTy): |
| 3710 | + format_parts.append(PrintfValidator.escape_str(arg_ty.value)) |
| 3711 | + else: |
| 3712 | + tile_ty = require_tile_type(arg_var) |
| 3713 | + format_parts.append(PrintfValidator.infer_format(get_dtype(tile_ty))) |
| 3714 | + leaf_vars.append(arg_var) |
| 3715 | + |
| 3716 | + format_parts.append(end_str) |
| 3717 | + final_format = ''.join(format_parts) |
| 3718 | + add_operation(TilePrintf, (), format=final_format, args=tuple(leaf_vars)) |
| 3719 | + |
| 3720 | + |
3641 | 3721 | @dataclass(eq=False) |
3642 | 3722 | class TileAssert(Operation, opcode="assert", memory_effect=MemoryEffect.STORE): |
3643 | 3723 | message: str = attribute() |
|
0 commit comments