Skip to content

Printf

printf

i8 = builtin.IntegerType(8) module-attribute

Printf = Dialect('printf', [PrintFormatOp, PrintCharOp, PrintIntOp], []) module-attribute

PrintFormatOp

Bases: IRDLOperation

A string formatting and printing utility.

Can be though of as a printf equivalent but with python style format strings.

Example uses:
%42 = arith.constant 42 : i32
printf.print_format "The magic number is {}

", %42

Source code in xdsl/dialects/printf.py
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
@irdl_op_definition
class PrintFormatOp(IRDLOperation):
    """
    A string formatting and printing utility.

    Can be though of as a printf equivalent but with python style format strings.

    Example uses:
    %42 = arith.constant 42 : i32
    printf.print_format "The magic number is {}\n", %42
    """

    name = "printf.print_format"

    format_str = attr_def(builtin.StringAttr)
    format_vals = var_operand_def()

    def __init__(self, format_str: str, *vals: SSAValue | Operation):
        super().__init__(
            operands=[vals], attributes={"format_str": builtin.StringAttr(format_str)}
        )

    def verify_(self) -> None:
        num_of_templates = self.format_str.data.count("{}")
        if not num_of_templates == len(self.format_vals):
            raise VerifyException(
                "Number of templates in template string must match number of arguments!"
            )

    def print(self, printer: Printer):
        printer.print_string(" ")
        printer.print_attribute(self.format_str)

        def print_val_and_type(ssa_val: SSAValue):
            printer.print_ssa_value(ssa_val)
            printer.print_string(" : ")
            printer.print_attribute(ssa_val.type)

        if len(self.format_vals) > 0:
            printer.print_string(", ")
            printer.print_list(self.operands, print_val_and_type)

        if len(self.attributes) > 1:
            attrs = self.attributes.copy()
            attrs.pop("format_str")
            printer.print_op_attributes(attrs)

    @classmethod
    def parse(cls: type[PrintFormatOp], parser: Parser) -> PrintFormatOp:
        format_str = parser.parse_str_literal()
        args: list[SSAValue] = []
        while parser.parse_optional_characters(",") is not None:
            args.append(arg := parser.parse_operand())
            parser.parse_characters(":", " - all arguments must have a type")
            arg_type = parser.parse_type()
            if arg.type != arg_type:
                parser.raise_error(f"Parsed ssa vlue {arg} must be of type {arg_type}")

        attr_dict = parser.parse_optional_attr_dict()

        if "format_str" in attr_dict:
            parser.raise_error(
                "format_str keyword is a reserved attribute for printf.print_format!"
            )

        op = PrintFormatOp(format_str, *args)

        op.attributes.update(attr_dict)

        return op

name = 'printf.print_format' class-attribute instance-attribute

format_str = attr_def(builtin.StringAttr) class-attribute instance-attribute

format_vals = var_operand_def() class-attribute instance-attribute

__init__(format_str: str, *vals: SSAValue | Operation)

Source code in xdsl/dialects/printf.py
35
36
37
38
def __init__(self, format_str: str, *vals: SSAValue | Operation):
    super().__init__(
        operands=[vals], attributes={"format_str": builtin.StringAttr(format_str)}
    )

verify_() -> None

Source code in xdsl/dialects/printf.py
40
41
42
43
44
45
def verify_(self) -> None:
    num_of_templates = self.format_str.data.count("{}")
    if not num_of_templates == len(self.format_vals):
        raise VerifyException(
            "Number of templates in template string must match number of arguments!"
        )

print(printer: Printer)

Source code in xdsl/dialects/printf.py
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
def print(self, printer: Printer):
    printer.print_string(" ")
    printer.print_attribute(self.format_str)

    def print_val_and_type(ssa_val: SSAValue):
        printer.print_ssa_value(ssa_val)
        printer.print_string(" : ")
        printer.print_attribute(ssa_val.type)

    if len(self.format_vals) > 0:
        printer.print_string(", ")
        printer.print_list(self.operands, print_val_and_type)

    if len(self.attributes) > 1:
        attrs = self.attributes.copy()
        attrs.pop("format_str")
        printer.print_op_attributes(attrs)

parse(parser: Parser) -> PrintFormatOp classmethod

Source code in xdsl/dialects/printf.py
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
@classmethod
def parse(cls: type[PrintFormatOp], parser: Parser) -> PrintFormatOp:
    format_str = parser.parse_str_literal()
    args: list[SSAValue] = []
    while parser.parse_optional_characters(",") is not None:
        args.append(arg := parser.parse_operand())
        parser.parse_characters(":", " - all arguments must have a type")
        arg_type = parser.parse_type()
        if arg.type != arg_type:
            parser.raise_error(f"Parsed ssa vlue {arg} must be of type {arg_type}")

    attr_dict = parser.parse_optional_attr_dict()

    if "format_str" in attr_dict:
        parser.raise_error(
            "format_str keyword is a reserved attribute for printf.print_format!"
        )

    op = PrintFormatOp(format_str, *args)

    op.attributes.update(attr_dict)

    return op

PrintCharOp

Bases: IRDLOperation

Print a single character

Equivalent to putchar in C, but uses signless bytes as input (instead of ui32). Unlike the C implementation, this op does not return anything.

Source code in xdsl/dialects/printf.py
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
@irdl_op_definition
class PrintCharOp(IRDLOperation):
    """
    Print a single character

    Equivalent to putchar in C, but uses signless bytes as input (instead of ui32).
    Unlike the C implementation, this op does not return anything.
    """

    name = "printf.print_char"
    char = operand_def(i8)

    def __init__(self, char: SSAValue | Operation):
        super().__init__(
            operands=[char],
        )

    @staticmethod
    def from_constant_char(char: str) -> PrintCharOp:
        """
        This constructor returns a PrintCharOp that prints the value supplied
        in "char" as a python char.
        """
        if len(char) != 1:
            raise ValueError(
                f'Unexpected char value "{char}", input must be a single ascii character'
            )
        ascii_value = ord(char)
        if ascii_value > 128:
            raise ValueError("Only ascii characters are supported")
        char_constant = arith.ConstantOp.from_int_and_width(ascii_value, i8)
        return PrintCharOp(char_constant)

name = 'printf.print_char' class-attribute instance-attribute

char = operand_def(i8) class-attribute instance-attribute

__init__(char: SSAValue | Operation)

Source code in xdsl/dialects/printf.py
102
103
104
105
def __init__(self, char: SSAValue | Operation):
    super().__init__(
        operands=[char],
    )

from_constant_char(char: str) -> PrintCharOp staticmethod

This constructor returns a PrintCharOp that prints the value supplied in "char" as a python char.

Source code in xdsl/dialects/printf.py
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
@staticmethod
def from_constant_char(char: str) -> PrintCharOp:
    """
    This constructor returns a PrintCharOp that prints the value supplied
    in "char" as a python char.
    """
    if len(char) != 1:
        raise ValueError(
            f'Unexpected char value "{char}", input must be a single ascii character'
        )
    ascii_value = ord(char)
    if ascii_value > 128:
        raise ValueError("Only ascii characters are supported")
    char_constant = arith.ConstantOp.from_int_and_width(ascii_value, i8)
    return PrintCharOp(char_constant)

PrintIntOp

Bases: IRDLOperation

Print a single Integer

Source code in xdsl/dialects/printf.py
124
125
126
127
128
129
130
131
132
133
134
135
136
@irdl_op_definition
class PrintIntOp(IRDLOperation):
    """
    Print a single Integer
    """

    name = "printf.print_int"
    int = operand_def(builtin.IntegerType)

    def __init__(self, integer: SSAValue | Operation):
        super().__init__(
            operands=[integer],
        )

name = 'printf.print_int' class-attribute instance-attribute

int = operand_def(builtin.IntegerType) class-attribute instance-attribute

__init__(integer: SSAValue | Operation)

Source code in xdsl/dialects/printf.py
133
134
135
136
def __init__(self, integer: SSAValue | Operation):
    super().__init__(
        operands=[integer],
    )