LLZK 3.0.0
An open-source IR for Zero Knowledge (ZK) circuits
Loading...
Searching...
No Matches
Attrs.td
Go to the documentation of this file.
1//===-- Attrs.td -------------------------------------------*- tablegen -*-===//
2//
3// Part of the LLZK Project, under the Apache License v2.0.
4// See LICENSE.txt for license information.
5// Copyright 2025 Veridise Inc.
6// SPDX-License-Identifier: Apache-2.0
7//
8//===----------------------------------------------------------------------===//
9
10#ifndef LLZK_FELT_ATTRS
11#define LLZK_FELT_ATTRS
12
13include "llzk/Dialect/Felt/IR/Dialect.td"
14include "llzk/Dialect/LLZK/IR/AttributeHelper.td"
15
16include "mlir/IR/AttrTypeBase.td"
17include "mlir/IR/BuiltinAttributeInterfaces.td"
18
19def LLZK_FeltConstAttr
20 : AttrDef<FeltDialect, "FeltConst", [TypedAttrInterface]> {
21 let mnemonic = "const";
22 let summary = "finite field element";
23 let description = [{
24 A felt attribute represents a finite field element.
25 }];
26
27 let parameters = (ins APIntParameter<"The felt constant value">:$value,
28 DefaultValuedParameter<"FeltType", "FeltType::get($_ctxt)">:$type);
29
30 let hasCustomAssemblyFormat = 1;
31
32 let builders = [
33 // Preserve the APInt-facing builder while using a canonical numeric
34 // storage key.
35 AttrBuilder<
36 (ins "::llvm::APInt":$value, "FeltType":$ty),
37 [{ return $_get(context, ::llzk::APIntValue(std::move(value)), ty); }]>,
38 // Like the default builder but with convenience overloads for
39 // constructing the APInt.
40 AttrBuilder<
41 (ins "unsigned":$numBits, "::llvm::StringRef":$str, "FeltType":$ty),
42 [{ return $_get(context, ::llvm::APInt(numBits, str, 10), ty); }]>,
43 AttrBuilder<
44 (ins "unsigned":$numBits, "::llvm::ArrayRef<uint64_t>":$parts,
45 "FeltType":$ty),
46 [{ return $_get(context, ::llvm::APInt(numBits, parts), ty); }]>,
47 // All APInt combinations but using felt type with unspecified field.
48 AttrBuilder<(ins "::llvm::APInt":$value),
49 [{ return get(context, value, FeltType::get(context)); }]>,
50 AttrBuilder<
51 (ins "unsigned":$numBits, "::llvm::StringRef":$str),
52 [{ return get(context, numBits, str, FeltType::get(context)); }]>,
53 AttrBuilder<
54 (ins "unsigned":$numBits, "::llvm::ArrayRef<uint64_t>":$parts),
55 [{ return get(context, numBits, parts, FeltType::get(context)); }]>,
56 // All APInt combinations but using the field name to construct felt type.
57 AttrBuilder<
58 (ins "::llvm::APInt":$value, "::llvm::StringRef":$fieldName),
59 [{ return get(context, value, FeltType::get(context, fieldName)); }]>,
60 AttrBuilder<
61 (ins "unsigned":$numBits, "::llvm::StringRef":$str,
62 "::llvm::StringRef":$fieldName),
63 [{ return get(context, numBits, str, FeltType::get(context, fieldName)); }]>,
64 AttrBuilder<
65 (ins "unsigned":$numBits, "::llvm::ArrayRef<uint64_t>":$parts,
66 "::llvm::StringRef":$fieldName),
67 [{ return get(context, numBits, parts, FeltType::get(context, fieldName)); }]>];
68
69 let extraClassDeclaration = [{
70 operator ::llvm::APInt() const { return getValue(); }
71
72 /// Returns the field name from the stored FeltType, or a null StringAttr
73 /// if no type is stored.
74 ::mlir::StringAttr getFieldName() const;
75 }];
76}
77
78def LLZK_FieldSpecAttr : AttrDef<FeltDialect, "FieldSpec"> {
79 let mnemonic = "field";
80 let summary = "prime field specification";
81 let description = [{
82 A specification of a prime field for use by felt types.
83
84 These specifications are provided in the `llzk.fields` attribute on the root
85 module as either a single element or a flat array, for example:
86
87 module attributes {llzk.lang, llzk.fields = field<foo, 7> { ... }
88 module attributes {llzk.lang, llzk.fields = [field<>]} { ... }
89
90 Specifications should not be provided for built-in fields, which include:
91 - babybear
92 - bn128/bn254
93 - goldilocks
94 - grumpkin
95 - koalabear
96 - mersenne31
97 }];
98
99 let parameters = (ins "::mlir::StringAttr":$fieldName,
100 APIntParameter<"The prime modulus">:$prime);
101
102 // Format is [{ `<` $fieldName `,` $prime `>` }], but with custom parsing
103 // to enable caching of the Field object definition.
104 let hasCustomAssemblyFormat = 1;
105
106 let builders =
107 [AttrBuilder<
108 (ins "::mlir::StringAttr":$fieldName, "::llvm::APInt":$prime),
109 [{ return $_get(context, fieldName, ::llzk::APIntValue(std::move(prime))); }]>,
110 AttrBuilder<(ins "::llvm::StringRef":$fieldName, "unsigned":$numBits,
111 "::llvm::StringRef":$primeStr),
112 [{
113 return $_get(context, ::mlir::StringAttr::get(context, fieldName), ::llvm::APInt(numBits, primeStr, 10));
114 }]>,
115 AttrBuilder<(ins "::llvm::StringRef":$fieldName, "unsigned":$numBits,
116 "::llvm::ArrayRef<uint64_t>":$parts),
117 [{
118 return $_get(context, ::mlir::StringAttr::get(context, fieldName), ::llvm::APInt(numBits, parts));
119 }]>];
120}
121
122#endif // LLZK_FELT_ATTRS