[clang][modules] Don't prevent translation of FW_Private includes when explicitly...
[llvm-project.git] / mlir / test / CAPI / ir.c
blobc6425f80a8bce9c2aae699392691192ac9821a25
1 //===- ir.c - Simple test of C APIs ---------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM
4 // Exceptions.
5 // See https://llvm.org/LICENSE.txt for license information.
6 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7 //
8 //===----------------------------------------------------------------------===//
10 /* RUN: mlir-capi-ir-test 2>&1 | FileCheck %s
13 #include "mlir-c/IR.h"
14 #include "mlir-c/AffineExpr.h"
15 #include "mlir-c/AffineMap.h"
16 #include "mlir-c/BuiltinAttributes.h"
17 #include "mlir-c/BuiltinTypes.h"
18 #include "mlir-c/Diagnostics.h"
19 #include "mlir-c/Dialect/Func.h"
20 #include "mlir-c/IntegerSet.h"
21 #include "mlir-c/RegisterEverything.h"
22 #include "mlir-c/Support.h"
24 #include <assert.h>
25 #include <inttypes.h>
26 #include <math.h>
27 #include <stdio.h>
28 #include <stdlib.h>
29 #include <string.h>
31 static void registerAllUpstreamDialects(MlirContext ctx) {
32 MlirDialectRegistry registry = mlirDialectRegistryCreate();
33 mlirRegisterAllDialects(registry);
34 mlirContextAppendDialectRegistry(ctx, registry);
35 mlirDialectRegistryDestroy(registry);
38 struct ResourceDeleteUserData {
39 const char *name;
41 static struct ResourceDeleteUserData resourceI64BlobUserData = {
42 "resource_i64_blob"};
43 static void reportResourceDelete(void *userData, const void *data, size_t size,
44 size_t align) {
45 fprintf(stderr, "reportResourceDelete: %s\n",
46 ((struct ResourceDeleteUserData *)userData)->name);
49 void populateLoopBody(MlirContext ctx, MlirBlock loopBody,
50 MlirLocation location, MlirBlock funcBody) {
51 MlirValue iv = mlirBlockGetArgument(loopBody, 0);
52 MlirValue funcArg0 = mlirBlockGetArgument(funcBody, 0);
53 MlirValue funcArg1 = mlirBlockGetArgument(funcBody, 1);
54 MlirType f32Type =
55 mlirTypeParseGet(ctx, mlirStringRefCreateFromCString("f32"));
57 MlirOperationState loadLHSState = mlirOperationStateGet(
58 mlirStringRefCreateFromCString("memref.load"), location);
59 MlirValue loadLHSOperands[] = {funcArg0, iv};
60 mlirOperationStateAddOperands(&loadLHSState, 2, loadLHSOperands);
61 mlirOperationStateAddResults(&loadLHSState, 1, &f32Type);
62 MlirOperation loadLHS = mlirOperationCreate(&loadLHSState);
63 mlirBlockAppendOwnedOperation(loopBody, loadLHS);
65 MlirOperationState loadRHSState = mlirOperationStateGet(
66 mlirStringRefCreateFromCString("memref.load"), location);
67 MlirValue loadRHSOperands[] = {funcArg1, iv};
68 mlirOperationStateAddOperands(&loadRHSState, 2, loadRHSOperands);
69 mlirOperationStateAddResults(&loadRHSState, 1, &f32Type);
70 MlirOperation loadRHS = mlirOperationCreate(&loadRHSState);
71 mlirBlockAppendOwnedOperation(loopBody, loadRHS);
73 MlirOperationState addState = mlirOperationStateGet(
74 mlirStringRefCreateFromCString("arith.addf"), location);
75 MlirValue addOperands[] = {mlirOperationGetResult(loadLHS, 0),
76 mlirOperationGetResult(loadRHS, 0)};
77 mlirOperationStateAddOperands(&addState, 2, addOperands);
78 mlirOperationStateAddResults(&addState, 1, &f32Type);
79 MlirOperation add = mlirOperationCreate(&addState);
80 mlirBlockAppendOwnedOperation(loopBody, add);
82 MlirOperationState storeState = mlirOperationStateGet(
83 mlirStringRefCreateFromCString("memref.store"), location);
84 MlirValue storeOperands[] = {mlirOperationGetResult(add, 0), funcArg0, iv};
85 mlirOperationStateAddOperands(&storeState, 3, storeOperands);
86 MlirOperation store = mlirOperationCreate(&storeState);
87 mlirBlockAppendOwnedOperation(loopBody, store);
89 MlirOperationState yieldState = mlirOperationStateGet(
90 mlirStringRefCreateFromCString("scf.yield"), location);
91 MlirOperation yield = mlirOperationCreate(&yieldState);
92 mlirBlockAppendOwnedOperation(loopBody, yield);
95 MlirModule makeAndDumpAdd(MlirContext ctx, MlirLocation location) {
96 MlirModule moduleOp = mlirModuleCreateEmpty(location);
97 MlirBlock moduleBody = mlirModuleGetBody(moduleOp);
99 MlirType memrefType =
100 mlirTypeParseGet(ctx, mlirStringRefCreateFromCString("memref<?xf32>"));
101 MlirType funcBodyArgTypes[] = {memrefType, memrefType};
102 MlirLocation funcBodyArgLocs[] = {location, location};
103 MlirRegion funcBodyRegion = mlirRegionCreate();
104 MlirBlock funcBody =
105 mlirBlockCreate(sizeof(funcBodyArgTypes) / sizeof(MlirType),
106 funcBodyArgTypes, funcBodyArgLocs);
107 mlirRegionAppendOwnedBlock(funcBodyRegion, funcBody);
109 MlirAttribute funcTypeAttr = mlirAttributeParseGet(
110 ctx,
111 mlirStringRefCreateFromCString("(memref<?xf32>, memref<?xf32>) -> ()"));
112 MlirAttribute funcNameAttr =
113 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("\"add\""));
114 MlirNamedAttribute funcAttrs[] = {
115 mlirNamedAttributeGet(
116 mlirIdentifierGet(ctx,
117 mlirStringRefCreateFromCString("function_type")),
118 funcTypeAttr),
119 mlirNamedAttributeGet(
120 mlirIdentifierGet(ctx, mlirStringRefCreateFromCString("sym_name")),
121 funcNameAttr)};
122 MlirOperationState funcState = mlirOperationStateGet(
123 mlirStringRefCreateFromCString("func.func"), location);
124 mlirOperationStateAddAttributes(&funcState, 2, funcAttrs);
125 mlirOperationStateAddOwnedRegions(&funcState, 1, &funcBodyRegion);
126 MlirOperation func = mlirOperationCreate(&funcState);
127 mlirBlockInsertOwnedOperation(moduleBody, 0, func);
129 MlirType indexType =
130 mlirTypeParseGet(ctx, mlirStringRefCreateFromCString("index"));
131 MlirAttribute indexZeroLiteral =
132 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("0 : index"));
133 MlirNamedAttribute indexZeroValueAttr = mlirNamedAttributeGet(
134 mlirIdentifierGet(ctx, mlirStringRefCreateFromCString("value")),
135 indexZeroLiteral);
136 MlirOperationState constZeroState = mlirOperationStateGet(
137 mlirStringRefCreateFromCString("arith.constant"), location);
138 mlirOperationStateAddResults(&constZeroState, 1, &indexType);
139 mlirOperationStateAddAttributes(&constZeroState, 1, &indexZeroValueAttr);
140 MlirOperation constZero = mlirOperationCreate(&constZeroState);
141 mlirBlockAppendOwnedOperation(funcBody, constZero);
143 MlirValue funcArg0 = mlirBlockGetArgument(funcBody, 0);
144 MlirValue constZeroValue = mlirOperationGetResult(constZero, 0);
145 MlirValue dimOperands[] = {funcArg0, constZeroValue};
146 MlirOperationState dimState = mlirOperationStateGet(
147 mlirStringRefCreateFromCString("memref.dim"), location);
148 mlirOperationStateAddOperands(&dimState, 2, dimOperands);
149 mlirOperationStateAddResults(&dimState, 1, &indexType);
150 MlirOperation dim = mlirOperationCreate(&dimState);
151 mlirBlockAppendOwnedOperation(funcBody, dim);
153 MlirRegion loopBodyRegion = mlirRegionCreate();
154 MlirBlock loopBody = mlirBlockCreate(0, NULL, NULL);
155 mlirBlockAddArgument(loopBody, indexType, location);
156 mlirRegionAppendOwnedBlock(loopBodyRegion, loopBody);
158 MlirAttribute indexOneLiteral =
159 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("1 : index"));
160 MlirNamedAttribute indexOneValueAttr = mlirNamedAttributeGet(
161 mlirIdentifierGet(ctx, mlirStringRefCreateFromCString("value")),
162 indexOneLiteral);
163 MlirOperationState constOneState = mlirOperationStateGet(
164 mlirStringRefCreateFromCString("arith.constant"), location);
165 mlirOperationStateAddResults(&constOneState, 1, &indexType);
166 mlirOperationStateAddAttributes(&constOneState, 1, &indexOneValueAttr);
167 MlirOperation constOne = mlirOperationCreate(&constOneState);
168 mlirBlockAppendOwnedOperation(funcBody, constOne);
170 MlirValue dimValue = mlirOperationGetResult(dim, 0);
171 MlirValue constOneValue = mlirOperationGetResult(constOne, 0);
172 MlirValue loopOperands[] = {constZeroValue, dimValue, constOneValue};
173 MlirOperationState loopState = mlirOperationStateGet(
174 mlirStringRefCreateFromCString("scf.for"), location);
175 mlirOperationStateAddOperands(&loopState, 3, loopOperands);
176 mlirOperationStateAddOwnedRegions(&loopState, 1, &loopBodyRegion);
177 MlirOperation loop = mlirOperationCreate(&loopState);
178 mlirBlockAppendOwnedOperation(funcBody, loop);
180 populateLoopBody(ctx, loopBody, location, funcBody);
182 MlirOperationState retState = mlirOperationStateGet(
183 mlirStringRefCreateFromCString("func.return"), location);
184 MlirOperation ret = mlirOperationCreate(&retState);
185 mlirBlockAppendOwnedOperation(funcBody, ret);
187 MlirOperation module = mlirModuleGetOperation(moduleOp);
188 mlirOperationDump(module);
189 // clang-format off
190 // CHECK: module {
191 // CHECK: func @add(%[[ARG0:.*]]: memref<?xf32>, %[[ARG1:.*]]: memref<?xf32>) {
192 // CHECK: %[[C0:.*]] = arith.constant 0 : index
193 // CHECK: %[[DIM:.*]] = memref.dim %[[ARG0]], %[[C0]] : memref<?xf32>
194 // CHECK: %[[C1:.*]] = arith.constant 1 : index
195 // CHECK: scf.for %[[I:.*]] = %[[C0]] to %[[DIM]] step %[[C1]] {
196 // CHECK: %[[LHS:.*]] = memref.load %[[ARG0]][%[[I]]] : memref<?xf32>
197 // CHECK: %[[RHS:.*]] = memref.load %[[ARG1]][%[[I]]] : memref<?xf32>
198 // CHECK: %[[SUM:.*]] = arith.addf %[[LHS]], %[[RHS]] : f32
199 // CHECK: memref.store %[[SUM]], %[[ARG0]][%[[I]]] : memref<?xf32>
200 // CHECK: }
201 // CHECK: return
202 // CHECK: }
203 // CHECK: }
204 // clang-format on
206 return moduleOp;
209 struct OpListNode {
210 MlirOperation op;
211 struct OpListNode *next;
213 typedef struct OpListNode OpListNode;
215 struct ModuleStats {
216 unsigned numOperations;
217 unsigned numAttributes;
218 unsigned numBlocks;
219 unsigned numRegions;
220 unsigned numValues;
221 unsigned numBlockArguments;
222 unsigned numOpResults;
224 typedef struct ModuleStats ModuleStats;
226 int collectStatsSingle(OpListNode *head, ModuleStats *stats) {
227 MlirOperation operation = head->op;
228 stats->numOperations += 1;
229 stats->numValues += mlirOperationGetNumResults(operation);
230 stats->numAttributes += mlirOperationGetNumAttributes(operation);
232 unsigned numRegions = mlirOperationGetNumRegions(operation);
234 stats->numRegions += numRegions;
236 intptr_t numResults = mlirOperationGetNumResults(operation);
237 for (intptr_t i = 0; i < numResults; ++i) {
238 MlirValue result = mlirOperationGetResult(operation, i);
239 if (!mlirValueIsAOpResult(result))
240 return 1;
241 if (mlirValueIsABlockArgument(result))
242 return 2;
243 if (!mlirOperationEqual(operation, mlirOpResultGetOwner(result)))
244 return 3;
245 if (i != mlirOpResultGetResultNumber(result))
246 return 4;
247 ++stats->numOpResults;
250 MlirRegion region = mlirOperationGetFirstRegion(operation);
251 while (!mlirRegionIsNull(region)) {
252 for (MlirBlock block = mlirRegionGetFirstBlock(region);
253 !mlirBlockIsNull(block); block = mlirBlockGetNextInRegion(block)) {
254 ++stats->numBlocks;
255 intptr_t numArgs = mlirBlockGetNumArguments(block);
256 stats->numValues += numArgs;
257 for (intptr_t j = 0; j < numArgs; ++j) {
258 MlirValue arg = mlirBlockGetArgument(block, j);
259 if (!mlirValueIsABlockArgument(arg))
260 return 5;
261 if (mlirValueIsAOpResult(arg))
262 return 6;
263 if (!mlirBlockEqual(block, mlirBlockArgumentGetOwner(arg)))
264 return 7;
265 if (j != mlirBlockArgumentGetArgNumber(arg))
266 return 8;
267 ++stats->numBlockArguments;
270 for (MlirOperation child = mlirBlockGetFirstOperation(block);
271 !mlirOperationIsNull(child);
272 child = mlirOperationGetNextInBlock(child)) {
273 OpListNode *node = malloc(sizeof(OpListNode));
274 node->op = child;
275 node->next = head->next;
276 head->next = node;
279 region = mlirRegionGetNextInOperation(region);
281 return 0;
284 int collectStats(MlirOperation operation) {
285 OpListNode *head = malloc(sizeof(OpListNode));
286 head->op = operation;
287 head->next = NULL;
289 ModuleStats stats;
290 stats.numOperations = 0;
291 stats.numAttributes = 0;
292 stats.numBlocks = 0;
293 stats.numRegions = 0;
294 stats.numValues = 0;
295 stats.numBlockArguments = 0;
296 stats.numOpResults = 0;
298 do {
299 int retval = collectStatsSingle(head, &stats);
300 if (retval) {
301 free(head);
302 return retval;
304 OpListNode *next = head->next;
305 free(head);
306 head = next;
307 } while (head);
309 if (stats.numValues != stats.numBlockArguments + stats.numOpResults)
310 return 100;
312 fprintf(stderr, "@stats\n");
313 fprintf(stderr, "Number of operations: %u\n", stats.numOperations);
314 fprintf(stderr, "Number of attributes: %u\n", stats.numAttributes);
315 fprintf(stderr, "Number of blocks: %u\n", stats.numBlocks);
316 fprintf(stderr, "Number of regions: %u\n", stats.numRegions);
317 fprintf(stderr, "Number of values: %u\n", stats.numValues);
318 fprintf(stderr, "Number of block arguments: %u\n", stats.numBlockArguments);
319 fprintf(stderr, "Number of op results: %u\n", stats.numOpResults);
320 // clang-format off
321 // CHECK-LABEL: @stats
322 // CHECK: Number of operations: 12
323 // CHECK: Number of attributes: 5
324 // CHECK: Number of blocks: 3
325 // CHECK: Number of regions: 3
326 // CHECK: Number of values: 9
327 // CHECK: Number of block arguments: 3
328 // CHECK: Number of op results: 6
329 // clang-format on
330 return 0;
333 static void printToStderr(MlirStringRef str, void *userData) {
334 (void)userData;
335 fwrite(str.data, 1, str.length, stderr);
338 static void printFirstOfEach(MlirContext ctx, MlirOperation operation) {
339 // Assuming we are given a module, go to the first operation of the first
340 // function.
341 MlirRegion region = mlirOperationGetRegion(operation, 0);
342 MlirBlock block = mlirRegionGetFirstBlock(region);
343 operation = mlirBlockGetFirstOperation(block);
344 region = mlirOperationGetRegion(operation, 0);
345 MlirOperation parentOperation = operation;
346 block = mlirRegionGetFirstBlock(region);
347 operation = mlirBlockGetFirstOperation(block);
348 assert(mlirModuleIsNull(mlirModuleFromOperation(operation)));
350 // Verify that parent operation and block report correctly.
351 // CHECK: Parent operation eq: 1
352 fprintf(stderr, "Parent operation eq: %d\n",
353 mlirOperationEqual(mlirOperationGetParentOperation(operation),
354 parentOperation));
355 // CHECK: Block eq: 1
356 fprintf(stderr, "Block eq: %d\n",
357 mlirBlockEqual(mlirOperationGetBlock(operation), block));
358 // CHECK: Block parent operation eq: 1
359 fprintf(
360 stderr, "Block parent operation eq: %d\n",
361 mlirOperationEqual(mlirBlockGetParentOperation(block), parentOperation));
362 // CHECK: Block parent region eq: 1
363 fprintf(stderr, "Block parent region eq: %d\n",
364 mlirRegionEqual(mlirBlockGetParentRegion(block), region));
366 // In the module we created, the first operation of the first function is
367 // an "memref.dim", which has an attribute and a single result that we can
368 // use to test the printing mechanism.
369 mlirBlockPrint(block, printToStderr, NULL);
370 fprintf(stderr, "\n");
371 fprintf(stderr, "First operation: ");
372 mlirOperationPrint(operation, printToStderr, NULL);
373 fprintf(stderr, "\n");
374 // clang-format off
375 // CHECK: %[[C0:.*]] = arith.constant 0 : index
376 // CHECK: %[[DIM:.*]] = memref.dim %{{.*}}, %[[C0]] : memref<?xf32>
377 // CHECK: %[[C1:.*]] = arith.constant 1 : index
378 // CHECK: scf.for %[[I:.*]] = %[[C0]] to %[[DIM]] step %[[C1]] {
379 // CHECK: %[[LHS:.*]] = memref.load %{{.*}}[%[[I]]] : memref<?xf32>
380 // CHECK: %[[RHS:.*]] = memref.load %{{.*}}[%[[I]]] : memref<?xf32>
381 // CHECK: %[[SUM:.*]] = arith.addf %[[LHS]], %[[RHS]] : f32
382 // CHECK: memref.store %[[SUM]], %{{.*}}[%[[I]]] : memref<?xf32>
383 // CHECK: }
384 // CHECK: return
385 // CHECK: First operation: {{.*}} = arith.constant 0 : index
386 // clang-format on
388 // Get the operation name and print it.
389 MlirIdentifier ident = mlirOperationGetName(operation);
390 MlirStringRef identStr = mlirIdentifierStr(ident);
391 fprintf(stderr, "Operation name: '");
392 for (size_t i = 0; i < identStr.length; ++i)
393 fputc(identStr.data[i], stderr);
394 fprintf(stderr, "'\n");
395 // CHECK: Operation name: 'arith.constant'
397 // Get the identifier again and verify equal.
398 MlirIdentifier identAgain = mlirIdentifierGet(ctx, identStr);
399 fprintf(stderr, "Identifier equal: %d\n",
400 mlirIdentifierEqual(ident, identAgain));
401 // CHECK: Identifier equal: 1
403 // Get the block terminator and print it.
404 MlirOperation terminator = mlirBlockGetTerminator(block);
405 fprintf(stderr, "Terminator: ");
406 mlirOperationPrint(terminator, printToStderr, NULL);
407 fprintf(stderr, "\n");
408 // CHECK: Terminator: func.return
410 // Get the attribute by name.
411 bool hasValueAttr = mlirOperationHasInherentAttributeByName(
412 operation, mlirStringRefCreateFromCString("value"));
413 if (hasValueAttr)
414 // CHECK: Has attr "value"
415 fprintf(stderr, "Has attr \"value\"");
417 MlirAttribute valueAttr0 = mlirOperationGetInherentAttributeByName(
418 operation, mlirStringRefCreateFromCString("value"));
419 fprintf(stderr, "Get attr \"value\": ");
420 mlirAttributePrint(valueAttr0, printToStderr, NULL);
421 fprintf(stderr, "\n");
422 // CHECK: Get attr "value": 0 : index
424 // Get a non-existing attribute and assert that it is null (sanity).
425 fprintf(stderr, "does_not_exist is null: %d\n",
426 mlirAttributeIsNull(mlirOperationGetDiscardableAttributeByName(
427 operation, mlirStringRefCreateFromCString("does_not_exist"))));
428 // CHECK: does_not_exist is null: 1
430 // Get result 0 and its type.
431 MlirValue value = mlirOperationGetResult(operation, 0);
432 fprintf(stderr, "Result 0: ");
433 mlirValuePrint(value, printToStderr, NULL);
434 fprintf(stderr, "\n");
435 fprintf(stderr, "Value is null: %d\n", mlirValueIsNull(value));
436 // CHECK: Result 0: {{.*}} = arith.constant 0 : index
437 // CHECK: Value is null: 0
439 MlirType type = mlirValueGetType(value);
440 fprintf(stderr, "Result 0 type: ");
441 mlirTypePrint(type, printToStderr, NULL);
442 fprintf(stderr, "\n");
443 // CHECK: Result 0 type: index
445 // Set a discardable attribute.
446 mlirOperationSetDiscardableAttributeByName(
447 operation, mlirStringRefCreateFromCString("custom_attr"),
448 mlirBoolAttrGet(ctx, 1));
449 fprintf(stderr, "Op with set attr: ");
450 mlirOperationPrint(operation, printToStderr, NULL);
451 fprintf(stderr, "\n");
452 // CHECK: Op with set attr: {{.*}} {custom_attr = true}
454 // Remove the attribute.
455 fprintf(stderr, "Remove attr: %d\n",
456 mlirOperationRemoveDiscardableAttributeByName(
457 operation, mlirStringRefCreateFromCString("custom_attr")));
458 fprintf(stderr, "Remove attr again: %d\n",
459 mlirOperationRemoveDiscardableAttributeByName(
460 operation, mlirStringRefCreateFromCString("custom_attr")));
461 fprintf(stderr, "Removed attr is null: %d\n",
462 mlirAttributeIsNull(mlirOperationGetDiscardableAttributeByName(
463 operation, mlirStringRefCreateFromCString("custom_attr"))));
464 // CHECK: Remove attr: 1
465 // CHECK: Remove attr again: 0
466 // CHECK: Removed attr is null: 1
468 // Add a large attribute to verify printing flags.
469 int64_t eltsShape[] = {4};
470 int32_t eltsData[] = {1, 2, 3, 4};
471 mlirOperationSetDiscardableAttributeByName(
472 operation, mlirStringRefCreateFromCString("elts"),
473 mlirDenseElementsAttrInt32Get(
474 mlirRankedTensorTypeGet(1, eltsShape, mlirIntegerTypeGet(ctx, 32),
475 mlirAttributeGetNull()),
476 4, eltsData));
477 MlirOpPrintingFlags flags = mlirOpPrintingFlagsCreate();
478 mlirOpPrintingFlagsElideLargeElementsAttrs(flags, 2);
479 mlirOpPrintingFlagsPrintGenericOpForm(flags);
480 mlirOpPrintingFlagsEnableDebugInfo(flags, /*enable=*/1, /*prettyForm=*/0);
481 mlirOpPrintingFlagsUseLocalScope(flags);
482 fprintf(stderr, "Op print with all flags: ");
483 mlirOperationPrintWithFlags(operation, flags, printToStderr, NULL);
484 fprintf(stderr, "\n");
485 // clang-format off
486 // CHECK: Op print with all flags: %{{.*}} = "arith.constant"() <{value = 0 : index}> {elts = dense_resource<__elided__> : tensor<4xi32>} : () -> index loc(unknown)
487 // clang-format on
489 MlirAsmState state = mlirAsmStateCreateForOperation(parentOperation, flags);
490 fprintf(stderr, "With state: |");
491 mlirValuePrintAsOperand(value, state, printToStderr, NULL);
492 // CHECK: With state: |%0|
493 fprintf(stderr, "|\n");
494 mlirAsmStateDestroy(state);
496 mlirOpPrintingFlagsDestroy(flags);
499 static int constructAndTraverseIr(MlirContext ctx) {
500 MlirLocation location = mlirLocationUnknownGet(ctx);
502 MlirModule moduleOp = makeAndDumpAdd(ctx, location);
503 MlirOperation module = mlirModuleGetOperation(moduleOp);
504 assert(!mlirModuleIsNull(mlirModuleFromOperation(module)));
506 int errcode = collectStats(module);
507 if (errcode)
508 return errcode;
510 printFirstOfEach(ctx, module);
512 mlirModuleDestroy(moduleOp);
513 return 0;
516 /// Creates an operation with a region containing multiple blocks with
517 /// operations and dumps it. The blocks and operations are inserted using
518 /// block/operation-relative API and their final order is checked.
519 static void buildWithInsertionsAndPrint(MlirContext ctx) {
520 MlirLocation loc = mlirLocationUnknownGet(ctx);
521 mlirContextSetAllowUnregisteredDialects(ctx, true);
523 MlirRegion owningRegion = mlirRegionCreate();
524 MlirBlock nullBlock = mlirRegionGetFirstBlock(owningRegion);
525 MlirOperationState state = mlirOperationStateGet(
526 mlirStringRefCreateFromCString("insertion.order.test"), loc);
527 mlirOperationStateAddOwnedRegions(&state, 1, &owningRegion);
528 MlirOperation op = mlirOperationCreate(&state);
529 MlirRegion region = mlirOperationGetRegion(op, 0);
531 // Use integer types of different bitwidth as block arguments in order to
532 // differentiate blocks.
533 MlirType i1 = mlirIntegerTypeGet(ctx, 1);
534 MlirType i2 = mlirIntegerTypeGet(ctx, 2);
535 MlirType i3 = mlirIntegerTypeGet(ctx, 3);
536 MlirType i4 = mlirIntegerTypeGet(ctx, 4);
537 MlirType i5 = mlirIntegerTypeGet(ctx, 5);
538 MlirBlock block1 = mlirBlockCreate(1, &i1, &loc);
539 MlirBlock block2 = mlirBlockCreate(1, &i2, &loc);
540 MlirBlock block3 = mlirBlockCreate(1, &i3, &loc);
541 MlirBlock block4 = mlirBlockCreate(1, &i4, &loc);
542 MlirBlock block5 = mlirBlockCreate(1, &i5, &loc);
543 // Insert blocks so as to obtain the 1-2-3-4 order,
544 mlirRegionInsertOwnedBlockBefore(region, nullBlock, block3);
545 mlirRegionInsertOwnedBlockBefore(region, block3, block2);
546 mlirRegionInsertOwnedBlockAfter(region, nullBlock, block1);
547 mlirRegionInsertOwnedBlockAfter(region, block3, block4);
548 mlirRegionInsertOwnedBlockBefore(region, block3, block5);
550 MlirOperationState op1State =
551 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op1"), loc);
552 MlirOperationState op2State =
553 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op2"), loc);
554 MlirOperationState op3State =
555 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op3"), loc);
556 MlirOperationState op4State =
557 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op4"), loc);
558 MlirOperationState op5State =
559 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op5"), loc);
560 MlirOperationState op6State =
561 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op6"), loc);
562 MlirOperationState op7State =
563 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op7"), loc);
564 MlirOperationState op8State =
565 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op8"), loc);
566 MlirOperation op1 = mlirOperationCreate(&op1State);
567 MlirOperation op2 = mlirOperationCreate(&op2State);
568 MlirOperation op3 = mlirOperationCreate(&op3State);
569 MlirOperation op4 = mlirOperationCreate(&op4State);
570 MlirOperation op5 = mlirOperationCreate(&op5State);
571 MlirOperation op6 = mlirOperationCreate(&op6State);
572 MlirOperation op7 = mlirOperationCreate(&op7State);
573 MlirOperation op8 = mlirOperationCreate(&op8State);
575 // Insert operations in the first block so as to obtain the 1-2-3-4 order.
576 MlirOperation nullOperation = mlirBlockGetFirstOperation(block1);
577 assert(mlirOperationIsNull(nullOperation));
578 mlirBlockInsertOwnedOperationBefore(block1, nullOperation, op3);
579 mlirBlockInsertOwnedOperationBefore(block1, op3, op2);
580 mlirBlockInsertOwnedOperationAfter(block1, nullOperation, op1);
581 mlirBlockInsertOwnedOperationAfter(block1, op3, op4);
583 // Append operations to the rest of blocks to make them non-empty and thus
584 // printable.
585 mlirBlockAppendOwnedOperation(block2, op5);
586 mlirBlockAppendOwnedOperation(block3, op6);
587 mlirBlockAppendOwnedOperation(block4, op7);
588 mlirBlockAppendOwnedOperation(block5, op8);
590 // Remove block5.
591 mlirBlockDetach(block5);
592 mlirBlockDestroy(block5);
594 mlirOperationDump(op);
595 mlirOperationDestroy(op);
596 mlirContextSetAllowUnregisteredDialects(ctx, false);
597 // clang-format off
598 // CHECK-LABEL: "insertion.order.test"
599 // CHECK: ^{{.*}}(%{{.*}}: i1
600 // CHECK: "dummy.op1"
601 // CHECK-NEXT: "dummy.op2"
602 // CHECK-NEXT: "dummy.op3"
603 // CHECK-NEXT: "dummy.op4"
604 // CHECK: ^{{.*}}(%{{.*}}: i2
605 // CHECK: "dummy.op5"
606 // CHECK-NOT: ^{{.*}}(%{{.*}}: i5
607 // CHECK-NOT: "dummy.op8"
608 // CHECK: ^{{.*}}(%{{.*}}: i3
609 // CHECK: "dummy.op6"
610 // CHECK: ^{{.*}}(%{{.*}}: i4
611 // CHECK: "dummy.op7"
612 // clang-format on
615 /// Creates operations with type inference and tests various failure modes.
616 static int createOperationWithTypeInference(MlirContext ctx) {
617 MlirLocation loc = mlirLocationUnknownGet(ctx);
618 MlirAttribute iAttr = mlirIntegerAttrGet(mlirIntegerTypeGet(ctx, 32), 4);
620 // The shape.const_size op implements result type inference and is only used
621 // for that reason.
622 MlirOperationState state = mlirOperationStateGet(
623 mlirStringRefCreateFromCString("shape.const_size"), loc);
624 MlirNamedAttribute valueAttr = mlirNamedAttributeGet(
625 mlirIdentifierGet(ctx, mlirStringRefCreateFromCString("value")), iAttr);
626 mlirOperationStateAddAttributes(&state, 1, &valueAttr);
627 mlirOperationStateEnableResultTypeInference(&state);
629 // Expect result type inference to succeed.
630 MlirOperation op = mlirOperationCreate(&state);
631 if (mlirOperationIsNull(op)) {
632 fprintf(stderr, "ERROR: Result type inference unexpectedly failed");
633 return 1;
636 // CHECK: RESULT_TYPE_INFERENCE: !shape.size
637 fprintf(stderr, "RESULT_TYPE_INFERENCE: ");
638 mlirTypeDump(mlirValueGetType(mlirOperationGetResult(op, 0)));
639 fprintf(stderr, "\n");
640 mlirOperationDestroy(op);
641 return 0;
644 /// Dumps instances of all builtin types to check that C API works correctly.
645 /// Additionally, performs simple identity checks that a builtin type
646 /// constructed with C API can be inspected and has the expected type. The
647 /// latter achieves full coverage of C API for builtin types. Returns 0 on
648 /// success and a non-zero error code on failure.
649 static int printBuiltinTypes(MlirContext ctx) {
650 // Integer types.
651 MlirType i32 = mlirIntegerTypeGet(ctx, 32);
652 MlirType si32 = mlirIntegerTypeSignedGet(ctx, 32);
653 MlirType ui32 = mlirIntegerTypeUnsignedGet(ctx, 32);
654 if (!mlirTypeIsAInteger(i32) || mlirTypeIsAF32(i32))
655 return 1;
656 if (!mlirTypeIsAInteger(si32) || !mlirIntegerTypeIsSigned(si32))
657 return 2;
658 if (!mlirTypeIsAInteger(ui32) || !mlirIntegerTypeIsUnsigned(ui32))
659 return 3;
660 if (mlirTypeEqual(i32, ui32) || mlirTypeEqual(i32, si32))
661 return 4;
662 if (mlirIntegerTypeGetWidth(i32) != mlirIntegerTypeGetWidth(si32))
663 return 5;
664 fprintf(stderr, "@types\n");
665 mlirTypeDump(i32);
666 fprintf(stderr, "\n");
667 mlirTypeDump(si32);
668 fprintf(stderr, "\n");
669 mlirTypeDump(ui32);
670 fprintf(stderr, "\n");
671 // CHECK-LABEL: @types
672 // CHECK: i32
673 // CHECK: si32
674 // CHECK: ui32
676 // Index type.
677 MlirType index = mlirIndexTypeGet(ctx);
678 if (!mlirTypeIsAIndex(index))
679 return 6;
680 mlirTypeDump(index);
681 fprintf(stderr, "\n");
682 // CHECK: index
684 // Floating-point types.
685 MlirType bf16 = mlirBF16TypeGet(ctx);
686 MlirType f16 = mlirF16TypeGet(ctx);
687 MlirType f32 = mlirF32TypeGet(ctx);
688 MlirType f64 = mlirF64TypeGet(ctx);
689 if (!mlirTypeIsABF16(bf16))
690 return 7;
691 if (!mlirTypeIsAF16(f16))
692 return 9;
693 if (!mlirTypeIsAF32(f32))
694 return 10;
695 if (!mlirTypeIsAF64(f64))
696 return 11;
697 mlirTypeDump(bf16);
698 fprintf(stderr, "\n");
699 mlirTypeDump(f16);
700 fprintf(stderr, "\n");
701 mlirTypeDump(f32);
702 fprintf(stderr, "\n");
703 mlirTypeDump(f64);
704 fprintf(stderr, "\n");
705 // CHECK: bf16
706 // CHECK: f16
707 // CHECK: f32
708 // CHECK: f64
710 // None type.
711 MlirType none = mlirNoneTypeGet(ctx);
712 if (!mlirTypeIsANone(none))
713 return 12;
714 mlirTypeDump(none);
715 fprintf(stderr, "\n");
716 // CHECK: none
718 // Complex type.
719 MlirType cplx = mlirComplexTypeGet(f32);
720 if (!mlirTypeIsAComplex(cplx) ||
721 !mlirTypeEqual(mlirComplexTypeGetElementType(cplx), f32))
722 return 13;
723 mlirTypeDump(cplx);
724 fprintf(stderr, "\n");
725 // CHECK: complex<f32>
727 // Vector (and Shaped) type. ShapedType is a common base class for vectors,
728 // memrefs and tensors, one cannot create instances of this class so it is
729 // tested on an instance of vector type.
730 int64_t shape[] = {2, 3};
731 MlirType vector =
732 mlirVectorTypeGet(sizeof(shape) / sizeof(int64_t), shape, f32);
733 if (!mlirTypeIsAVector(vector) || !mlirTypeIsAShaped(vector))
734 return 14;
735 if (!mlirTypeEqual(mlirShapedTypeGetElementType(vector), f32) ||
736 !mlirShapedTypeHasRank(vector) || mlirShapedTypeGetRank(vector) != 2 ||
737 mlirShapedTypeGetDimSize(vector, 0) != 2 ||
738 mlirShapedTypeIsDynamicDim(vector, 0) ||
739 mlirShapedTypeGetDimSize(vector, 1) != 3 ||
740 !mlirShapedTypeHasStaticShape(vector))
741 return 15;
742 mlirTypeDump(vector);
743 fprintf(stderr, "\n");
744 // CHECK: vector<2x3xf32>
746 // Ranked tensor type.
747 MlirType rankedTensor = mlirRankedTensorTypeGet(
748 sizeof(shape) / sizeof(int64_t), shape, f32, mlirAttributeGetNull());
749 if (!mlirTypeIsATensor(rankedTensor) ||
750 !mlirTypeIsARankedTensor(rankedTensor) ||
751 !mlirAttributeIsNull(mlirRankedTensorTypeGetEncoding(rankedTensor)))
752 return 16;
753 mlirTypeDump(rankedTensor);
754 fprintf(stderr, "\n");
755 // CHECK: tensor<2x3xf32>
757 // Unranked tensor type.
758 MlirType unrankedTensor = mlirUnrankedTensorTypeGet(f32);
759 if (!mlirTypeIsATensor(unrankedTensor) ||
760 !mlirTypeIsAUnrankedTensor(unrankedTensor) ||
761 mlirShapedTypeHasRank(unrankedTensor))
762 return 17;
763 mlirTypeDump(unrankedTensor);
764 fprintf(stderr, "\n");
765 // CHECK: tensor<*xf32>
767 // MemRef type.
768 MlirAttribute memSpace2 = mlirIntegerAttrGet(mlirIntegerTypeGet(ctx, 64), 2);
769 MlirType memRef = mlirMemRefTypeContiguousGet(
770 f32, sizeof(shape) / sizeof(int64_t), shape, memSpace2);
771 if (!mlirTypeIsAMemRef(memRef) ||
772 !mlirAttributeEqual(mlirMemRefTypeGetMemorySpace(memRef), memSpace2))
773 return 18;
774 mlirTypeDump(memRef);
775 fprintf(stderr, "\n");
776 // CHECK: memref<2x3xf32, 2>
778 // Unranked MemRef type.
779 MlirAttribute memSpace4 = mlirIntegerAttrGet(mlirIntegerTypeGet(ctx, 64), 4);
780 MlirType unrankedMemRef = mlirUnrankedMemRefTypeGet(f32, memSpace4);
781 if (!mlirTypeIsAUnrankedMemRef(unrankedMemRef) ||
782 mlirTypeIsAMemRef(unrankedMemRef) ||
783 !mlirAttributeEqual(mlirUnrankedMemrefGetMemorySpace(unrankedMemRef),
784 memSpace4))
785 return 19;
786 mlirTypeDump(unrankedMemRef);
787 fprintf(stderr, "\n");
788 // CHECK: memref<*xf32, 4>
790 // Tuple type.
791 MlirType types[] = {unrankedMemRef, f32};
792 MlirType tuple = mlirTupleTypeGet(ctx, 2, types);
793 if (!mlirTypeIsATuple(tuple) || mlirTupleTypeGetNumTypes(tuple) != 2 ||
794 !mlirTypeEqual(mlirTupleTypeGetType(tuple, 0), unrankedMemRef) ||
795 !mlirTypeEqual(mlirTupleTypeGetType(tuple, 1), f32))
796 return 20;
797 mlirTypeDump(tuple);
798 fprintf(stderr, "\n");
799 // CHECK: tuple<memref<*xf32, 4>, f32>
801 // Function type.
802 MlirType funcInputs[2] = {mlirIndexTypeGet(ctx), mlirIntegerTypeGet(ctx, 1)};
803 MlirType funcResults[3] = {mlirIntegerTypeGet(ctx, 16),
804 mlirIntegerTypeGet(ctx, 32),
805 mlirIntegerTypeGet(ctx, 64)};
806 MlirType funcType = mlirFunctionTypeGet(ctx, 2, funcInputs, 3, funcResults);
807 if (mlirFunctionTypeGetNumInputs(funcType) != 2)
808 return 21;
809 if (mlirFunctionTypeGetNumResults(funcType) != 3)
810 return 22;
811 if (!mlirTypeEqual(funcInputs[0], mlirFunctionTypeGetInput(funcType, 0)) ||
812 !mlirTypeEqual(funcInputs[1], mlirFunctionTypeGetInput(funcType, 1)))
813 return 23;
814 if (!mlirTypeEqual(funcResults[0], mlirFunctionTypeGetResult(funcType, 0)) ||
815 !mlirTypeEqual(funcResults[1], mlirFunctionTypeGetResult(funcType, 1)) ||
816 !mlirTypeEqual(funcResults[2], mlirFunctionTypeGetResult(funcType, 2)))
817 return 24;
818 mlirTypeDump(funcType);
819 fprintf(stderr, "\n");
820 // CHECK: (index, i1) -> (i16, i32, i64)
822 // Opaque type.
823 MlirStringRef namespace = mlirStringRefCreate("dialect", 7);
824 MlirStringRef data = mlirStringRefCreate("type", 4);
825 mlirContextSetAllowUnregisteredDialects(ctx, true);
826 MlirType opaque = mlirOpaqueTypeGet(ctx, namespace, data);
827 mlirContextSetAllowUnregisteredDialects(ctx, false);
828 if (!mlirTypeIsAOpaque(opaque) ||
829 !mlirStringRefEqual(mlirOpaqueTypeGetDialectNamespace(opaque),
830 namespace) ||
831 !mlirStringRefEqual(mlirOpaqueTypeGetData(opaque), data))
832 return 25;
833 mlirTypeDump(opaque);
834 fprintf(stderr, "\n");
835 // CHECK: !dialect.type
837 return 0;
840 void callbackSetFixedLengthString(const char *data, intptr_t len,
841 void *userData) {
842 strncpy(userData, data, len);
845 bool stringIsEqual(const char *lhs, MlirStringRef rhs) {
846 if (strlen(lhs) != rhs.length) {
847 return false;
849 return !strncmp(lhs, rhs.data, rhs.length);
852 int printBuiltinAttributes(MlirContext ctx) {
853 MlirAttribute floating =
854 mlirFloatAttrDoubleGet(ctx, mlirF64TypeGet(ctx), 2.0);
855 if (!mlirAttributeIsAFloat(floating) ||
856 fabs(mlirFloatAttrGetValueDouble(floating) - 2.0) > 1E-6)
857 return 1;
858 fprintf(stderr, "@attrs\n");
859 mlirAttributeDump(floating);
860 // CHECK-LABEL: @attrs
861 // CHECK: 2.000000e+00 : f64
863 // Exercise mlirAttributeGetType() just for the first one.
864 MlirType floatingType = mlirAttributeGetType(floating);
865 mlirTypeDump(floatingType);
866 // CHECK: f64
868 MlirAttribute integer = mlirIntegerAttrGet(mlirIntegerTypeGet(ctx, 32), 42);
869 MlirAttribute signedInteger =
870 mlirIntegerAttrGet(mlirIntegerTypeSignedGet(ctx, 8), -1);
871 MlirAttribute unsignedInteger =
872 mlirIntegerAttrGet(mlirIntegerTypeUnsignedGet(ctx, 8), 255);
873 if (!mlirAttributeIsAInteger(integer) ||
874 mlirIntegerAttrGetValueInt(integer) != 42 ||
875 mlirIntegerAttrGetValueSInt(signedInteger) != -1 ||
876 mlirIntegerAttrGetValueUInt(unsignedInteger) != 255)
877 return 2;
878 mlirAttributeDump(integer);
879 mlirAttributeDump(signedInteger);
880 mlirAttributeDump(unsignedInteger);
881 // CHECK: 42 : i32
882 // CHECK: -1 : si8
883 // CHECK: 255 : ui8
885 MlirAttribute boolean = mlirBoolAttrGet(ctx, 1);
886 if (!mlirAttributeIsABool(boolean) || !mlirBoolAttrGetValue(boolean))
887 return 3;
888 mlirAttributeDump(boolean);
889 // CHECK: true
891 const char data[] = "abcdefghijklmnopqestuvwxyz";
892 MlirAttribute opaque =
893 mlirOpaqueAttrGet(ctx, mlirStringRefCreateFromCString("func"), 3, data,
894 mlirNoneTypeGet(ctx));
895 if (!mlirAttributeIsAOpaque(opaque) ||
896 !stringIsEqual("func", mlirOpaqueAttrGetDialectNamespace(opaque)))
897 return 4;
899 MlirStringRef opaqueData = mlirOpaqueAttrGetData(opaque);
900 if (opaqueData.length != 3 ||
901 strncmp(data, opaqueData.data, opaqueData.length))
902 return 5;
903 mlirAttributeDump(opaque);
904 // CHECK: #func.abc
906 MlirAttribute string =
907 mlirStringAttrGet(ctx, mlirStringRefCreate(data + 3, 2));
908 if (!mlirAttributeIsAString(string))
909 return 6;
911 MlirStringRef stringValue = mlirStringAttrGetValue(string);
912 if (stringValue.length != 2 ||
913 strncmp(data + 3, stringValue.data, stringValue.length))
914 return 7;
915 mlirAttributeDump(string);
916 // CHECK: "de"
918 MlirAttribute flatSymbolRef =
919 mlirFlatSymbolRefAttrGet(ctx, mlirStringRefCreate(data + 5, 3));
920 if (!mlirAttributeIsAFlatSymbolRef(flatSymbolRef))
921 return 8;
923 MlirStringRef flatSymbolRefValue =
924 mlirFlatSymbolRefAttrGetValue(flatSymbolRef);
925 if (flatSymbolRefValue.length != 3 ||
926 strncmp(data + 5, flatSymbolRefValue.data, flatSymbolRefValue.length))
927 return 9;
928 mlirAttributeDump(flatSymbolRef);
929 // CHECK: @fgh
931 MlirAttribute symbols[] = {flatSymbolRef, flatSymbolRef};
932 MlirAttribute symbolRef =
933 mlirSymbolRefAttrGet(ctx, mlirStringRefCreate(data + 8, 2), 2, symbols);
934 if (!mlirAttributeIsASymbolRef(symbolRef) ||
935 mlirSymbolRefAttrGetNumNestedReferences(symbolRef) != 2 ||
936 !mlirAttributeEqual(mlirSymbolRefAttrGetNestedReference(symbolRef, 0),
937 flatSymbolRef) ||
938 !mlirAttributeEqual(mlirSymbolRefAttrGetNestedReference(symbolRef, 1),
939 flatSymbolRef))
940 return 10;
942 MlirStringRef symbolRefLeaf = mlirSymbolRefAttrGetLeafReference(symbolRef);
943 MlirStringRef symbolRefRoot = mlirSymbolRefAttrGetRootReference(symbolRef);
944 if (symbolRefLeaf.length != 3 ||
945 strncmp(data + 5, symbolRefLeaf.data, symbolRefLeaf.length) ||
946 symbolRefRoot.length != 2 ||
947 strncmp(data + 8, symbolRefRoot.data, symbolRefRoot.length))
948 return 11;
949 mlirAttributeDump(symbolRef);
950 // CHECK: @ij::@fgh::@fgh
952 MlirAttribute type = mlirTypeAttrGet(mlirF32TypeGet(ctx));
953 if (!mlirAttributeIsAType(type) ||
954 !mlirTypeEqual(mlirF32TypeGet(ctx), mlirTypeAttrGetValue(type)))
955 return 12;
956 mlirAttributeDump(type);
957 // CHECK: f32
959 MlirAttribute unit = mlirUnitAttrGet(ctx);
960 if (!mlirAttributeIsAUnit(unit))
961 return 13;
962 mlirAttributeDump(unit);
963 // CHECK: unit
965 int64_t shape[] = {1, 2};
967 int bools[] = {0, 1};
968 uint8_t uints8[] = {0u, 1u};
969 int8_t ints8[] = {0, 1};
970 uint16_t uints16[] = {0u, 1u};
971 int16_t ints16[] = {0, 1};
972 uint32_t uints32[] = {0u, 1u};
973 int32_t ints32[] = {0, 1};
974 uint64_t uints64[] = {0u, 1u};
975 int64_t ints64[] = {0, 1};
976 float floats[] = {0.0f, 1.0f};
977 double doubles[] = {0.0, 1.0};
978 uint16_t bf16s[] = {0x0, 0x3f80};
979 uint16_t f16s[] = {0x0, 0x3c00};
980 MlirAttribute encoding = mlirAttributeGetNull();
981 MlirAttribute boolElements = mlirDenseElementsAttrBoolGet(
982 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 1), encoding),
983 2, bools);
984 MlirAttribute uint8Elements = mlirDenseElementsAttrUInt8Get(
985 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 8),
986 encoding),
987 2, uints8);
988 MlirAttribute int8Elements = mlirDenseElementsAttrInt8Get(
989 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 8), encoding),
990 2, ints8);
991 MlirAttribute uint16Elements = mlirDenseElementsAttrUInt16Get(
992 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 16),
993 encoding),
994 2, uints16);
995 MlirAttribute int16Elements = mlirDenseElementsAttrInt16Get(
996 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 16), encoding),
997 2, ints16);
998 MlirAttribute uint32Elements = mlirDenseElementsAttrUInt32Get(
999 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 32),
1000 encoding),
1001 2, uints32);
1002 MlirAttribute int32Elements = mlirDenseElementsAttrInt32Get(
1003 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 32), encoding),
1004 2, ints32);
1005 MlirAttribute uint64Elements = mlirDenseElementsAttrUInt64Get(
1006 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 64),
1007 encoding),
1008 2, uints64);
1009 MlirAttribute int64Elements = mlirDenseElementsAttrInt64Get(
1010 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 64), encoding),
1011 2, ints64);
1012 MlirAttribute floatElements = mlirDenseElementsAttrFloatGet(
1013 mlirRankedTensorTypeGet(2, shape, mlirF32TypeGet(ctx), encoding), 2,
1014 floats);
1015 MlirAttribute doubleElements = mlirDenseElementsAttrDoubleGet(
1016 mlirRankedTensorTypeGet(2, shape, mlirF64TypeGet(ctx), encoding), 2,
1017 doubles);
1018 MlirAttribute bf16Elements = mlirDenseElementsAttrBFloat16Get(
1019 mlirRankedTensorTypeGet(2, shape, mlirBF16TypeGet(ctx), encoding), 2,
1020 bf16s);
1021 MlirAttribute f16Elements = mlirDenseElementsAttrFloat16Get(
1022 mlirRankedTensorTypeGet(2, shape, mlirF16TypeGet(ctx), encoding), 2,
1023 f16s);
1025 if (!mlirAttributeIsADenseElements(boolElements) ||
1026 !mlirAttributeIsADenseElements(uint8Elements) ||
1027 !mlirAttributeIsADenseElements(int8Elements) ||
1028 !mlirAttributeIsADenseElements(uint32Elements) ||
1029 !mlirAttributeIsADenseElements(int32Elements) ||
1030 !mlirAttributeIsADenseElements(uint64Elements) ||
1031 !mlirAttributeIsADenseElements(int64Elements) ||
1032 !mlirAttributeIsADenseElements(floatElements) ||
1033 !mlirAttributeIsADenseElements(doubleElements) ||
1034 !mlirAttributeIsADenseElements(bf16Elements) ||
1035 !mlirAttributeIsADenseElements(f16Elements))
1036 return 14;
1038 if (mlirDenseElementsAttrGetBoolValue(boolElements, 1) != 1 ||
1039 mlirDenseElementsAttrGetUInt8Value(uint8Elements, 1) != 1 ||
1040 mlirDenseElementsAttrGetInt8Value(int8Elements, 1) != 1 ||
1041 mlirDenseElementsAttrGetUInt16Value(uint16Elements, 1) != 1 ||
1042 mlirDenseElementsAttrGetInt16Value(int16Elements, 1) != 1 ||
1043 mlirDenseElementsAttrGetUInt32Value(uint32Elements, 1) != 1 ||
1044 mlirDenseElementsAttrGetInt32Value(int32Elements, 1) != 1 ||
1045 mlirDenseElementsAttrGetUInt64Value(uint64Elements, 1) != 1 ||
1046 mlirDenseElementsAttrGetInt64Value(int64Elements, 1) != 1 ||
1047 fabsf(mlirDenseElementsAttrGetFloatValue(floatElements, 1) - 1.0f) >
1048 1E-6f ||
1049 fabs(mlirDenseElementsAttrGetDoubleValue(doubleElements, 1) - 1.0) > 1E-6)
1050 return 15;
1052 mlirAttributeDump(boolElements);
1053 mlirAttributeDump(uint8Elements);
1054 mlirAttributeDump(int8Elements);
1055 mlirAttributeDump(uint32Elements);
1056 mlirAttributeDump(int32Elements);
1057 mlirAttributeDump(uint64Elements);
1058 mlirAttributeDump(int64Elements);
1059 mlirAttributeDump(floatElements);
1060 mlirAttributeDump(doubleElements);
1061 mlirAttributeDump(bf16Elements);
1062 mlirAttributeDump(f16Elements);
1063 // CHECK: dense<{{\[}}[false, true]]> : tensor<1x2xi1>
1064 // CHECK: dense<{{\[}}[0, 1]]> : tensor<1x2xui8>
1065 // CHECK: dense<{{\[}}[0, 1]]> : tensor<1x2xi8>
1066 // CHECK: dense<{{\[}}[0, 1]]> : tensor<1x2xui32>
1067 // CHECK: dense<{{\[}}[0, 1]]> : tensor<1x2xi32>
1068 // CHECK: dense<{{\[}}[0, 1]]> : tensor<1x2xui64>
1069 // CHECK: dense<{{\[}}[0, 1]]> : tensor<1x2xi64>
1070 // CHECK: dense<{{\[}}[0.000000e+00, 1.000000e+00]]> : tensor<1x2xf32>
1071 // CHECK: dense<{{\[}}[0.000000e+00, 1.000000e+00]]> : tensor<1x2xf64>
1072 // CHECK: dense<{{\[}}[0.000000e+00, 1.000000e+00]]> : tensor<1x2xbf16>
1073 // CHECK: dense<{{\[}}[0.000000e+00, 1.000000e+00]]> : tensor<1x2xf16>
1075 MlirAttribute splatBool = mlirDenseElementsAttrBoolSplatGet(
1076 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 1), encoding),
1078 MlirAttribute splatUInt8 = mlirDenseElementsAttrUInt8SplatGet(
1079 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 8),
1080 encoding),
1082 MlirAttribute splatInt8 = mlirDenseElementsAttrInt8SplatGet(
1083 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 8), encoding),
1085 MlirAttribute splatUInt32 = mlirDenseElementsAttrUInt32SplatGet(
1086 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 32),
1087 encoding),
1089 MlirAttribute splatInt32 = mlirDenseElementsAttrInt32SplatGet(
1090 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 32), encoding),
1092 MlirAttribute splatUInt64 = mlirDenseElementsAttrUInt64SplatGet(
1093 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 64),
1094 encoding),
1096 MlirAttribute splatInt64 = mlirDenseElementsAttrInt64SplatGet(
1097 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 64), encoding),
1099 MlirAttribute splatFloat = mlirDenseElementsAttrFloatSplatGet(
1100 mlirRankedTensorTypeGet(2, shape, mlirF32TypeGet(ctx), encoding), 1.0f);
1101 MlirAttribute splatDouble = mlirDenseElementsAttrDoubleSplatGet(
1102 mlirRankedTensorTypeGet(2, shape, mlirF64TypeGet(ctx), encoding), 1.0);
1104 if (!mlirAttributeIsADenseElements(splatBool) ||
1105 !mlirDenseElementsAttrIsSplat(splatBool) ||
1106 !mlirAttributeIsADenseElements(splatUInt8) ||
1107 !mlirDenseElementsAttrIsSplat(splatUInt8) ||
1108 !mlirAttributeIsADenseElements(splatInt8) ||
1109 !mlirDenseElementsAttrIsSplat(splatInt8) ||
1110 !mlirAttributeIsADenseElements(splatUInt32) ||
1111 !mlirDenseElementsAttrIsSplat(splatUInt32) ||
1112 !mlirAttributeIsADenseElements(splatInt32) ||
1113 !mlirDenseElementsAttrIsSplat(splatInt32) ||
1114 !mlirAttributeIsADenseElements(splatUInt64) ||
1115 !mlirDenseElementsAttrIsSplat(splatUInt64) ||
1116 !mlirAttributeIsADenseElements(splatInt64) ||
1117 !mlirDenseElementsAttrIsSplat(splatInt64) ||
1118 !mlirAttributeIsADenseElements(splatFloat) ||
1119 !mlirDenseElementsAttrIsSplat(splatFloat) ||
1120 !mlirAttributeIsADenseElements(splatDouble) ||
1121 !mlirDenseElementsAttrIsSplat(splatDouble))
1122 return 16;
1124 if (mlirDenseElementsAttrGetBoolSplatValue(splatBool) != 1 ||
1125 mlirDenseElementsAttrGetUInt8SplatValue(splatUInt8) != 1 ||
1126 mlirDenseElementsAttrGetInt8SplatValue(splatInt8) != 1 ||
1127 mlirDenseElementsAttrGetUInt32SplatValue(splatUInt32) != 1 ||
1128 mlirDenseElementsAttrGetInt32SplatValue(splatInt32) != 1 ||
1129 mlirDenseElementsAttrGetUInt64SplatValue(splatUInt64) != 1 ||
1130 mlirDenseElementsAttrGetInt64SplatValue(splatInt64) != 1 ||
1131 fabsf(mlirDenseElementsAttrGetFloatSplatValue(splatFloat) - 1.0f) >
1132 1E-6f ||
1133 fabs(mlirDenseElementsAttrGetDoubleSplatValue(splatDouble) - 1.0) > 1E-6)
1134 return 17;
1136 const uint8_t *uint8RawData =
1137 (const uint8_t *)mlirDenseElementsAttrGetRawData(uint8Elements);
1138 const int8_t *int8RawData =
1139 (const int8_t *)mlirDenseElementsAttrGetRawData(int8Elements);
1140 const uint32_t *uint32RawData =
1141 (const uint32_t *)mlirDenseElementsAttrGetRawData(uint32Elements);
1142 const int32_t *int32RawData =
1143 (const int32_t *)mlirDenseElementsAttrGetRawData(int32Elements);
1144 const uint64_t *uint64RawData =
1145 (const uint64_t *)mlirDenseElementsAttrGetRawData(uint64Elements);
1146 const int64_t *int64RawData =
1147 (const int64_t *)mlirDenseElementsAttrGetRawData(int64Elements);
1148 const float *floatRawData =
1149 (const float *)mlirDenseElementsAttrGetRawData(floatElements);
1150 const double *doubleRawData =
1151 (const double *)mlirDenseElementsAttrGetRawData(doubleElements);
1152 const uint16_t *bf16RawData =
1153 (const uint16_t *)mlirDenseElementsAttrGetRawData(bf16Elements);
1154 const uint16_t *f16RawData =
1155 (const uint16_t *)mlirDenseElementsAttrGetRawData(f16Elements);
1156 if (uint8RawData[0] != 0u || uint8RawData[1] != 1u || int8RawData[0] != 0 ||
1157 int8RawData[1] != 1 || uint32RawData[0] != 0u || uint32RawData[1] != 1u ||
1158 int32RawData[0] != 0 || int32RawData[1] != 1 || uint64RawData[0] != 0u ||
1159 uint64RawData[1] != 1u || int64RawData[0] != 0 || int64RawData[1] != 1 ||
1160 floatRawData[0] != 0.0f || floatRawData[1] != 1.0f ||
1161 doubleRawData[0] != 0.0 || doubleRawData[1] != 1.0 ||
1162 bf16RawData[0] != 0 || bf16RawData[1] != 0x3f80 || f16RawData[0] != 0 ||
1163 f16RawData[1] != 0x3c00)
1164 return 18;
1166 mlirAttributeDump(splatBool);
1167 mlirAttributeDump(splatUInt8);
1168 mlirAttributeDump(splatInt8);
1169 mlirAttributeDump(splatUInt32);
1170 mlirAttributeDump(splatInt32);
1171 mlirAttributeDump(splatUInt64);
1172 mlirAttributeDump(splatInt64);
1173 mlirAttributeDump(splatFloat);
1174 mlirAttributeDump(splatDouble);
1175 // CHECK: dense<true> : tensor<1x2xi1>
1176 // CHECK: dense<1> : tensor<1x2xui8>
1177 // CHECK: dense<1> : tensor<1x2xi8>
1178 // CHECK: dense<1> : tensor<1x2xui32>
1179 // CHECK: dense<1> : tensor<1x2xi32>
1180 // CHECK: dense<1> : tensor<1x2xui64>
1181 // CHECK: dense<1> : tensor<1x2xi64>
1182 // CHECK: dense<1.000000e+00> : tensor<1x2xf32>
1183 // CHECK: dense<1.000000e+00> : tensor<1x2xf64>
1185 mlirAttributeDump(mlirElementsAttrGetValue(floatElements, 2, uints64));
1186 mlirAttributeDump(mlirElementsAttrGetValue(doubleElements, 2, uints64));
1187 mlirAttributeDump(mlirElementsAttrGetValue(bf16Elements, 2, uints64));
1188 mlirAttributeDump(mlirElementsAttrGetValue(f16Elements, 2, uints64));
1189 // CHECK: 1.000000e+00 : f32
1190 // CHECK: 1.000000e+00 : f64
1191 // CHECK: 1.000000e+00 : bf16
1192 // CHECK: 1.000000e+00 : f16
1194 int64_t indices[] = {0, 1};
1195 int64_t one = 1;
1196 MlirAttribute indicesAttr = mlirDenseElementsAttrInt64Get(
1197 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 64), encoding),
1198 2, indices);
1199 MlirAttribute valuesAttr = mlirDenseElementsAttrFloatGet(
1200 mlirRankedTensorTypeGet(1, &one, mlirF32TypeGet(ctx), encoding), 1,
1201 floats);
1202 MlirAttribute sparseAttr = mlirSparseElementsAttribute(
1203 mlirRankedTensorTypeGet(2, shape, mlirF32TypeGet(ctx), encoding),
1204 indicesAttr, valuesAttr);
1205 mlirAttributeDump(sparseAttr);
1206 // CHECK: sparse<{{\[}}[0, 1]], 0.000000e+00> : tensor<1x2xf32>
1208 MlirAttribute boolArray = mlirDenseBoolArrayGet(ctx, 2, bools);
1209 MlirAttribute int8Array = mlirDenseI8ArrayGet(ctx, 2, ints8);
1210 MlirAttribute int16Array = mlirDenseI16ArrayGet(ctx, 2, ints16);
1211 MlirAttribute int32Array = mlirDenseI32ArrayGet(ctx, 2, ints32);
1212 MlirAttribute int64Array = mlirDenseI64ArrayGet(ctx, 2, ints64);
1213 MlirAttribute floatArray = mlirDenseF32ArrayGet(ctx, 2, floats);
1214 MlirAttribute doubleArray = mlirDenseF64ArrayGet(ctx, 2, doubles);
1215 if (!mlirAttributeIsADenseBoolArray(boolArray) ||
1216 !mlirAttributeIsADenseI8Array(int8Array) ||
1217 !mlirAttributeIsADenseI16Array(int16Array) ||
1218 !mlirAttributeIsADenseI32Array(int32Array) ||
1219 !mlirAttributeIsADenseI64Array(int64Array) ||
1220 !mlirAttributeIsADenseF32Array(floatArray) ||
1221 !mlirAttributeIsADenseF64Array(doubleArray))
1222 return 19;
1224 if (mlirDenseArrayGetNumElements(boolArray) != 2 ||
1225 mlirDenseArrayGetNumElements(int8Array) != 2 ||
1226 mlirDenseArrayGetNumElements(int16Array) != 2 ||
1227 mlirDenseArrayGetNumElements(int32Array) != 2 ||
1228 mlirDenseArrayGetNumElements(int64Array) != 2 ||
1229 mlirDenseArrayGetNumElements(floatArray) != 2 ||
1230 mlirDenseArrayGetNumElements(doubleArray) != 2)
1231 return 20;
1233 if (mlirDenseBoolArrayGetElement(boolArray, 1) != 1 ||
1234 mlirDenseI8ArrayGetElement(int8Array, 1) != 1 ||
1235 mlirDenseI16ArrayGetElement(int16Array, 1) != 1 ||
1236 mlirDenseI32ArrayGetElement(int32Array, 1) != 1 ||
1237 mlirDenseI64ArrayGetElement(int64Array, 1) != 1 ||
1238 fabsf(mlirDenseF32ArrayGetElement(floatArray, 1) - 1.0f) > 1E-6f ||
1239 fabs(mlirDenseF64ArrayGetElement(doubleArray, 1) - 1.0) > 1E-6)
1240 return 21;
1242 int64_t layoutStrides[3] = {5, 7, 13};
1243 MlirAttribute stridedLayoutAttr =
1244 mlirStridedLayoutAttrGet(ctx, 42, 3, &layoutStrides[0]);
1246 // CHECK: strided<[5, 7, 13], offset: 42>
1247 mlirAttributeDump(stridedLayoutAttr);
1249 if (mlirStridedLayoutAttrGetOffset(stridedLayoutAttr) != 42 ||
1250 mlirStridedLayoutAttrGetNumStrides(stridedLayoutAttr) != 3 ||
1251 mlirStridedLayoutAttrGetStride(stridedLayoutAttr, 0) != 5 ||
1252 mlirStridedLayoutAttrGetStride(stridedLayoutAttr, 1) != 7 ||
1253 mlirStridedLayoutAttrGetStride(stridedLayoutAttr, 2) != 13)
1254 return 22;
1256 MlirAttribute uint8Blob = mlirUnmanagedDenseUInt8ResourceElementsAttrGet(
1257 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 8),
1258 encoding),
1259 mlirStringRefCreateFromCString("resource_ui8"), 2, uints8);
1260 MlirAttribute uint16Blob = mlirUnmanagedDenseUInt16ResourceElementsAttrGet(
1261 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 16),
1262 encoding),
1263 mlirStringRefCreateFromCString("resource_ui16"), 2, uints16);
1264 MlirAttribute uint32Blob = mlirUnmanagedDenseUInt32ResourceElementsAttrGet(
1265 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 32),
1266 encoding),
1267 mlirStringRefCreateFromCString("resource_ui32"), 2, uints32);
1268 MlirAttribute uint64Blob = mlirUnmanagedDenseUInt64ResourceElementsAttrGet(
1269 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeUnsignedGet(ctx, 64),
1270 encoding),
1271 mlirStringRefCreateFromCString("resource_ui64"), 2, uints64);
1272 MlirAttribute int8Blob = mlirUnmanagedDenseInt8ResourceElementsAttrGet(
1273 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 8), encoding),
1274 mlirStringRefCreateFromCString("resource_i8"), 2, ints8);
1275 MlirAttribute int16Blob = mlirUnmanagedDenseInt16ResourceElementsAttrGet(
1276 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 16), encoding),
1277 mlirStringRefCreateFromCString("resource_i16"), 2, ints16);
1278 MlirAttribute int32Blob = mlirUnmanagedDenseInt32ResourceElementsAttrGet(
1279 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 32), encoding),
1280 mlirStringRefCreateFromCString("resource_i32"), 2, ints32);
1281 MlirAttribute int64Blob = mlirUnmanagedDenseInt64ResourceElementsAttrGet(
1282 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 64), encoding),
1283 mlirStringRefCreateFromCString("resource_i64"), 2, ints64);
1284 MlirAttribute floatsBlob = mlirUnmanagedDenseFloatResourceElementsAttrGet(
1285 mlirRankedTensorTypeGet(2, shape, mlirF32TypeGet(ctx), encoding),
1286 mlirStringRefCreateFromCString("resource_f32"), 2, floats);
1287 MlirAttribute doublesBlob = mlirUnmanagedDenseDoubleResourceElementsAttrGet(
1288 mlirRankedTensorTypeGet(2, shape, mlirF64TypeGet(ctx), encoding),
1289 mlirStringRefCreateFromCString("resource_f64"), 2, doubles);
1290 MlirAttribute blobBlob = mlirUnmanagedDenseResourceElementsAttrGet(
1291 mlirRankedTensorTypeGet(2, shape, mlirIntegerTypeGet(ctx, 64), encoding),
1292 mlirStringRefCreateFromCString("resource_i64_blob"), /*data=*/uints64,
1293 /*dataLength=*/sizeof(uints64),
1294 /*dataAlignment=*/_Alignof(uint64_t),
1295 /*dataIsMutable=*/false,
1296 /*deleter=*/reportResourceDelete,
1297 /*userData=*/(void *)&resourceI64BlobUserData);
1299 mlirAttributeDump(uint8Blob);
1300 mlirAttributeDump(uint16Blob);
1301 mlirAttributeDump(uint32Blob);
1302 mlirAttributeDump(uint64Blob);
1303 mlirAttributeDump(int8Blob);
1304 mlirAttributeDump(int16Blob);
1305 mlirAttributeDump(int32Blob);
1306 mlirAttributeDump(int64Blob);
1307 mlirAttributeDump(floatsBlob);
1308 mlirAttributeDump(doublesBlob);
1309 mlirAttributeDump(blobBlob);
1310 // CHECK: dense_resource<resource_ui8> : tensor<1x2xui8>
1311 // CHECK: dense_resource<resource_ui16> : tensor<1x2xui16>
1312 // CHECK: dense_resource<resource_ui32> : tensor<1x2xui32>
1313 // CHECK: dense_resource<resource_ui64> : tensor<1x2xui64>
1314 // CHECK: dense_resource<resource_i8> : tensor<1x2xi8>
1315 // CHECK: dense_resource<resource_i16> : tensor<1x2xi16>
1316 // CHECK: dense_resource<resource_i32> : tensor<1x2xi32>
1317 // CHECK: dense_resource<resource_i64> : tensor<1x2xi64>
1318 // CHECK: dense_resource<resource_f32> : tensor<1x2xf32>
1319 // CHECK: dense_resource<resource_f64> : tensor<1x2xf64>
1320 // CHECK: dense_resource<resource_i64_blob> : tensor<1x2xi64>
1322 if (mlirDenseUInt8ResourceElementsAttrGetValue(uint8Blob, 1) != 1 ||
1323 mlirDenseUInt16ResourceElementsAttrGetValue(uint16Blob, 1) != 1 ||
1324 mlirDenseUInt32ResourceElementsAttrGetValue(uint32Blob, 1) != 1 ||
1325 mlirDenseUInt64ResourceElementsAttrGetValue(uint64Blob, 1) != 1 ||
1326 mlirDenseInt8ResourceElementsAttrGetValue(int8Blob, 1) != 1 ||
1327 mlirDenseInt16ResourceElementsAttrGetValue(int16Blob, 1) != 1 ||
1328 mlirDenseInt32ResourceElementsAttrGetValue(int32Blob, 1) != 1 ||
1329 mlirDenseInt64ResourceElementsAttrGetValue(int64Blob, 1) != 1 ||
1330 fabsf(mlirDenseF32ArrayGetElement(floatArray, 1) - 1.0f) > 1E-6f ||
1331 fabsf(mlirDenseFloatResourceElementsAttrGetValue(floatsBlob, 1) - 1.0f) >
1332 1e-6 ||
1333 fabs(mlirDenseDoubleResourceElementsAttrGetValue(doublesBlob, 1) - 1.0f) >
1334 1e-6 ||
1335 mlirDenseUInt64ResourceElementsAttrGetValue(blobBlob, 1) != 1)
1336 return 23;
1338 MlirLocation loc = mlirLocationUnknownGet(ctx);
1339 MlirAttribute locAttr = mlirLocationGetAttribute(loc);
1340 if (!mlirAttributeIsALocation(locAttr))
1341 return 24;
1343 return 0;
1346 int printAffineMap(MlirContext ctx) {
1347 MlirAffineMap emptyAffineMap = mlirAffineMapEmptyGet(ctx);
1348 MlirAffineMap affineMap = mlirAffineMapZeroResultGet(ctx, 3, 2);
1349 MlirAffineMap constAffineMap = mlirAffineMapConstantGet(ctx, 2);
1350 MlirAffineMap multiDimIdentityAffineMap =
1351 mlirAffineMapMultiDimIdentityGet(ctx, 3);
1352 MlirAffineMap minorIdentityAffineMap =
1353 mlirAffineMapMinorIdentityGet(ctx, 3, 2);
1354 unsigned permutation[] = {1, 2, 0};
1355 MlirAffineMap permutationAffineMap = mlirAffineMapPermutationGet(
1356 ctx, sizeof(permutation) / sizeof(unsigned), permutation);
1358 fprintf(stderr, "@affineMap\n");
1359 mlirAffineMapDump(emptyAffineMap);
1360 mlirAffineMapDump(affineMap);
1361 mlirAffineMapDump(constAffineMap);
1362 mlirAffineMapDump(multiDimIdentityAffineMap);
1363 mlirAffineMapDump(minorIdentityAffineMap);
1364 mlirAffineMapDump(permutationAffineMap);
1365 // CHECK-LABEL: @affineMap
1366 // CHECK: () -> ()
1367 // CHECK: (d0, d1, d2)[s0, s1] -> ()
1368 // CHECK: () -> (2)
1369 // CHECK: (d0, d1, d2) -> (d0, d1, d2)
1370 // CHECK: (d0, d1, d2) -> (d1, d2)
1371 // CHECK: (d0, d1, d2) -> (d1, d2, d0)
1373 if (!mlirAffineMapIsIdentity(emptyAffineMap) ||
1374 mlirAffineMapIsIdentity(affineMap) ||
1375 mlirAffineMapIsIdentity(constAffineMap) ||
1376 !mlirAffineMapIsIdentity(multiDimIdentityAffineMap) ||
1377 mlirAffineMapIsIdentity(minorIdentityAffineMap) ||
1378 mlirAffineMapIsIdentity(permutationAffineMap))
1379 return 1;
1381 if (!mlirAffineMapIsMinorIdentity(emptyAffineMap) ||
1382 mlirAffineMapIsMinorIdentity(affineMap) ||
1383 !mlirAffineMapIsMinorIdentity(multiDimIdentityAffineMap) ||
1384 !mlirAffineMapIsMinorIdentity(minorIdentityAffineMap) ||
1385 mlirAffineMapIsMinorIdentity(permutationAffineMap))
1386 return 2;
1388 if (!mlirAffineMapIsEmpty(emptyAffineMap) ||
1389 mlirAffineMapIsEmpty(affineMap) || mlirAffineMapIsEmpty(constAffineMap) ||
1390 mlirAffineMapIsEmpty(multiDimIdentityAffineMap) ||
1391 mlirAffineMapIsEmpty(minorIdentityAffineMap) ||
1392 mlirAffineMapIsEmpty(permutationAffineMap))
1393 return 3;
1395 if (mlirAffineMapIsSingleConstant(emptyAffineMap) ||
1396 mlirAffineMapIsSingleConstant(affineMap) ||
1397 !mlirAffineMapIsSingleConstant(constAffineMap) ||
1398 mlirAffineMapIsSingleConstant(multiDimIdentityAffineMap) ||
1399 mlirAffineMapIsSingleConstant(minorIdentityAffineMap) ||
1400 mlirAffineMapIsSingleConstant(permutationAffineMap))
1401 return 4;
1403 if (mlirAffineMapGetSingleConstantResult(constAffineMap) != 2)
1404 return 5;
1406 if (mlirAffineMapGetNumDims(emptyAffineMap) != 0 ||
1407 mlirAffineMapGetNumDims(affineMap) != 3 ||
1408 mlirAffineMapGetNumDims(constAffineMap) != 0 ||
1409 mlirAffineMapGetNumDims(multiDimIdentityAffineMap) != 3 ||
1410 mlirAffineMapGetNumDims(minorIdentityAffineMap) != 3 ||
1411 mlirAffineMapGetNumDims(permutationAffineMap) != 3)
1412 return 6;
1414 if (mlirAffineMapGetNumSymbols(emptyAffineMap) != 0 ||
1415 mlirAffineMapGetNumSymbols(affineMap) != 2 ||
1416 mlirAffineMapGetNumSymbols(constAffineMap) != 0 ||
1417 mlirAffineMapGetNumSymbols(multiDimIdentityAffineMap) != 0 ||
1418 mlirAffineMapGetNumSymbols(minorIdentityAffineMap) != 0 ||
1419 mlirAffineMapGetNumSymbols(permutationAffineMap) != 0)
1420 return 7;
1422 if (mlirAffineMapGetNumResults(emptyAffineMap) != 0 ||
1423 mlirAffineMapGetNumResults(affineMap) != 0 ||
1424 mlirAffineMapGetNumResults(constAffineMap) != 1 ||
1425 mlirAffineMapGetNumResults(multiDimIdentityAffineMap) != 3 ||
1426 mlirAffineMapGetNumResults(minorIdentityAffineMap) != 2 ||
1427 mlirAffineMapGetNumResults(permutationAffineMap) != 3)
1428 return 8;
1430 if (mlirAffineMapGetNumInputs(emptyAffineMap) != 0 ||
1431 mlirAffineMapGetNumInputs(affineMap) != 5 ||
1432 mlirAffineMapGetNumInputs(constAffineMap) != 0 ||
1433 mlirAffineMapGetNumInputs(multiDimIdentityAffineMap) != 3 ||
1434 mlirAffineMapGetNumInputs(minorIdentityAffineMap) != 3 ||
1435 mlirAffineMapGetNumInputs(permutationAffineMap) != 3)
1436 return 9;
1438 if (!mlirAffineMapIsProjectedPermutation(emptyAffineMap) ||
1439 !mlirAffineMapIsPermutation(emptyAffineMap) ||
1440 mlirAffineMapIsProjectedPermutation(affineMap) ||
1441 mlirAffineMapIsPermutation(affineMap) ||
1442 mlirAffineMapIsProjectedPermutation(constAffineMap) ||
1443 mlirAffineMapIsPermutation(constAffineMap) ||
1444 !mlirAffineMapIsProjectedPermutation(multiDimIdentityAffineMap) ||
1445 !mlirAffineMapIsPermutation(multiDimIdentityAffineMap) ||
1446 !mlirAffineMapIsProjectedPermutation(minorIdentityAffineMap) ||
1447 mlirAffineMapIsPermutation(minorIdentityAffineMap) ||
1448 !mlirAffineMapIsProjectedPermutation(permutationAffineMap) ||
1449 !mlirAffineMapIsPermutation(permutationAffineMap))
1450 return 10;
1452 intptr_t sub[] = {1};
1454 MlirAffineMap subMap = mlirAffineMapGetSubMap(
1455 multiDimIdentityAffineMap, sizeof(sub) / sizeof(intptr_t), sub);
1456 MlirAffineMap majorSubMap =
1457 mlirAffineMapGetMajorSubMap(multiDimIdentityAffineMap, 1);
1458 MlirAffineMap minorSubMap =
1459 mlirAffineMapGetMinorSubMap(multiDimIdentityAffineMap, 1);
1461 mlirAffineMapDump(subMap);
1462 mlirAffineMapDump(majorSubMap);
1463 mlirAffineMapDump(minorSubMap);
1464 // CHECK: (d0, d1, d2) -> (d1)
1465 // CHECK: (d0, d1, d2) -> (d0)
1466 // CHECK: (d0, d1, d2) -> (d2)
1468 return 0;
1471 int printAffineExpr(MlirContext ctx) {
1472 MlirAffineExpr affineDimExpr = mlirAffineDimExprGet(ctx, 5);
1473 MlirAffineExpr affineSymbolExpr = mlirAffineSymbolExprGet(ctx, 5);
1474 MlirAffineExpr affineConstantExpr = mlirAffineConstantExprGet(ctx, 5);
1475 MlirAffineExpr affineAddExpr =
1476 mlirAffineAddExprGet(affineDimExpr, affineSymbolExpr);
1477 MlirAffineExpr affineMulExpr =
1478 mlirAffineMulExprGet(affineDimExpr, affineSymbolExpr);
1479 MlirAffineExpr affineModExpr =
1480 mlirAffineModExprGet(affineDimExpr, affineSymbolExpr);
1481 MlirAffineExpr affineFloorDivExpr =
1482 mlirAffineFloorDivExprGet(affineDimExpr, affineSymbolExpr);
1483 MlirAffineExpr affineCeilDivExpr =
1484 mlirAffineCeilDivExprGet(affineDimExpr, affineSymbolExpr);
1486 // Tests mlirAffineExprDump.
1487 fprintf(stderr, "@affineExpr\n");
1488 mlirAffineExprDump(affineDimExpr);
1489 mlirAffineExprDump(affineSymbolExpr);
1490 mlirAffineExprDump(affineConstantExpr);
1491 mlirAffineExprDump(affineAddExpr);
1492 mlirAffineExprDump(affineMulExpr);
1493 mlirAffineExprDump(affineModExpr);
1494 mlirAffineExprDump(affineFloorDivExpr);
1495 mlirAffineExprDump(affineCeilDivExpr);
1496 // CHECK-LABEL: @affineExpr
1497 // CHECK: d5
1498 // CHECK: s5
1499 // CHECK: 5
1500 // CHECK: d5 + s5
1501 // CHECK: d5 * s5
1502 // CHECK: d5 mod s5
1503 // CHECK: d5 floordiv s5
1504 // CHECK: d5 ceildiv s5
1506 // Tests methods of affine binary operation expression, takes add expression
1507 // as an example.
1508 mlirAffineExprDump(mlirAffineBinaryOpExprGetLHS(affineAddExpr));
1509 mlirAffineExprDump(mlirAffineBinaryOpExprGetRHS(affineAddExpr));
1510 // CHECK: d5
1511 // CHECK: s5
1513 // Tests methods of affine dimension expression.
1514 if (mlirAffineDimExprGetPosition(affineDimExpr) != 5)
1515 return 1;
1517 // Tests methods of affine symbol expression.
1518 if (mlirAffineSymbolExprGetPosition(affineSymbolExpr) != 5)
1519 return 2;
1521 // Tests methods of affine constant expression.
1522 if (mlirAffineConstantExprGetValue(affineConstantExpr) != 5)
1523 return 3;
1525 // Tests methods of affine expression.
1526 if (mlirAffineExprIsSymbolicOrConstant(affineDimExpr) ||
1527 !mlirAffineExprIsSymbolicOrConstant(affineSymbolExpr) ||
1528 !mlirAffineExprIsSymbolicOrConstant(affineConstantExpr) ||
1529 mlirAffineExprIsSymbolicOrConstant(affineAddExpr) ||
1530 mlirAffineExprIsSymbolicOrConstant(affineMulExpr) ||
1531 mlirAffineExprIsSymbolicOrConstant(affineModExpr) ||
1532 mlirAffineExprIsSymbolicOrConstant(affineFloorDivExpr) ||
1533 mlirAffineExprIsSymbolicOrConstant(affineCeilDivExpr))
1534 return 4;
1536 if (!mlirAffineExprIsPureAffine(affineDimExpr) ||
1537 !mlirAffineExprIsPureAffine(affineSymbolExpr) ||
1538 !mlirAffineExprIsPureAffine(affineConstantExpr) ||
1539 !mlirAffineExprIsPureAffine(affineAddExpr) ||
1540 mlirAffineExprIsPureAffine(affineMulExpr) ||
1541 mlirAffineExprIsPureAffine(affineModExpr) ||
1542 mlirAffineExprIsPureAffine(affineFloorDivExpr) ||
1543 mlirAffineExprIsPureAffine(affineCeilDivExpr))
1544 return 5;
1546 if (mlirAffineExprGetLargestKnownDivisor(affineDimExpr) != 1 ||
1547 mlirAffineExprGetLargestKnownDivisor(affineSymbolExpr) != 1 ||
1548 mlirAffineExprGetLargestKnownDivisor(affineConstantExpr) != 5 ||
1549 mlirAffineExprGetLargestKnownDivisor(affineAddExpr) != 1 ||
1550 mlirAffineExprGetLargestKnownDivisor(affineMulExpr) != 1 ||
1551 mlirAffineExprGetLargestKnownDivisor(affineModExpr) != 1 ||
1552 mlirAffineExprGetLargestKnownDivisor(affineFloorDivExpr) != 1 ||
1553 mlirAffineExprGetLargestKnownDivisor(affineCeilDivExpr) != 1)
1554 return 6;
1556 if (!mlirAffineExprIsMultipleOf(affineDimExpr, 1) ||
1557 !mlirAffineExprIsMultipleOf(affineSymbolExpr, 1) ||
1558 !mlirAffineExprIsMultipleOf(affineConstantExpr, 5) ||
1559 !mlirAffineExprIsMultipleOf(affineAddExpr, 1) ||
1560 !mlirAffineExprIsMultipleOf(affineMulExpr, 1) ||
1561 !mlirAffineExprIsMultipleOf(affineModExpr, 1) ||
1562 !mlirAffineExprIsMultipleOf(affineFloorDivExpr, 1) ||
1563 !mlirAffineExprIsMultipleOf(affineCeilDivExpr, 1))
1564 return 7;
1566 if (!mlirAffineExprIsFunctionOfDim(affineDimExpr, 5) ||
1567 mlirAffineExprIsFunctionOfDim(affineSymbolExpr, 5) ||
1568 mlirAffineExprIsFunctionOfDim(affineConstantExpr, 5) ||
1569 !mlirAffineExprIsFunctionOfDim(affineAddExpr, 5) ||
1570 !mlirAffineExprIsFunctionOfDim(affineMulExpr, 5) ||
1571 !mlirAffineExprIsFunctionOfDim(affineModExpr, 5) ||
1572 !mlirAffineExprIsFunctionOfDim(affineFloorDivExpr, 5) ||
1573 !mlirAffineExprIsFunctionOfDim(affineCeilDivExpr, 5))
1574 return 8;
1576 // Tests 'IsA' methods of affine binary operation expression.
1577 if (!mlirAffineExprIsAAdd(affineAddExpr))
1578 return 9;
1580 if (!mlirAffineExprIsAMul(affineMulExpr))
1581 return 10;
1583 if (!mlirAffineExprIsAMod(affineModExpr))
1584 return 11;
1586 if (!mlirAffineExprIsAFloorDiv(affineFloorDivExpr))
1587 return 12;
1589 if (!mlirAffineExprIsACeilDiv(affineCeilDivExpr))
1590 return 13;
1592 if (!mlirAffineExprIsABinary(affineAddExpr))
1593 return 14;
1595 // Test other 'IsA' method on affine expressions.
1596 if (!mlirAffineExprIsAConstant(affineConstantExpr))
1597 return 15;
1599 if (!mlirAffineExprIsADim(affineDimExpr))
1600 return 16;
1602 if (!mlirAffineExprIsASymbol(affineSymbolExpr))
1603 return 17;
1605 // Test equality and nullity.
1606 MlirAffineExpr otherDimExpr = mlirAffineDimExprGet(ctx, 5);
1607 if (!mlirAffineExprEqual(affineDimExpr, otherDimExpr))
1608 return 18;
1610 if (mlirAffineExprIsNull(affineDimExpr))
1611 return 19;
1613 return 0;
1616 int affineMapFromExprs(MlirContext ctx) {
1617 MlirAffineExpr affineDimExpr = mlirAffineDimExprGet(ctx, 0);
1618 MlirAffineExpr affineSymbolExpr = mlirAffineSymbolExprGet(ctx, 1);
1619 MlirAffineExpr exprs[] = {affineDimExpr, affineSymbolExpr};
1620 MlirAffineMap map = mlirAffineMapGet(ctx, 3, 3, 2, exprs);
1622 // CHECK-LABEL: @affineMapFromExprs
1623 fprintf(stderr, "@affineMapFromExprs");
1624 // CHECK: (d0, d1, d2)[s0, s1, s2] -> (d0, s1)
1625 mlirAffineMapDump(map);
1627 if (mlirAffineMapGetNumResults(map) != 2)
1628 return 1;
1630 if (!mlirAffineExprEqual(mlirAffineMapGetResult(map, 0), affineDimExpr))
1631 return 2;
1633 if (!mlirAffineExprEqual(mlirAffineMapGetResult(map, 1), affineSymbolExpr))
1634 return 3;
1636 MlirAffineExpr affineDim2Expr = mlirAffineDimExprGet(ctx, 1);
1637 MlirAffineExpr composed = mlirAffineExprCompose(affineDim2Expr, map);
1638 // CHECK: s1
1639 mlirAffineExprDump(composed);
1640 if (!mlirAffineExprEqual(composed, affineSymbolExpr))
1641 return 4;
1643 return 0;
1646 int printIntegerSet(MlirContext ctx) {
1647 MlirIntegerSet emptySet = mlirIntegerSetEmptyGet(ctx, 2, 1);
1649 // CHECK-LABEL: @printIntegerSet
1650 fprintf(stderr, "@printIntegerSet");
1652 // CHECK: (d0, d1)[s0] : (1 == 0)
1653 mlirIntegerSetDump(emptySet);
1655 if (!mlirIntegerSetIsCanonicalEmpty(emptySet))
1656 return 1;
1658 MlirIntegerSet anotherEmptySet = mlirIntegerSetEmptyGet(ctx, 2, 1);
1659 if (!mlirIntegerSetEqual(emptySet, anotherEmptySet))
1660 return 2;
1662 // Construct a set constrained by:
1663 // d0 - s0 == 0,
1664 // d1 - 42 >= 0.
1665 MlirAffineExpr negOne = mlirAffineConstantExprGet(ctx, -1);
1666 MlirAffineExpr negFortyTwo = mlirAffineConstantExprGet(ctx, -42);
1667 MlirAffineExpr d0 = mlirAffineDimExprGet(ctx, 0);
1668 MlirAffineExpr d1 = mlirAffineDimExprGet(ctx, 1);
1669 MlirAffineExpr s0 = mlirAffineSymbolExprGet(ctx, 0);
1670 MlirAffineExpr negS0 = mlirAffineMulExprGet(negOne, s0);
1671 MlirAffineExpr d0minusS0 = mlirAffineAddExprGet(d0, negS0);
1672 MlirAffineExpr d1minus42 = mlirAffineAddExprGet(d1, negFortyTwo);
1673 MlirAffineExpr constraints[] = {d0minusS0, d1minus42};
1674 bool flags[] = {true, false};
1676 MlirIntegerSet set = mlirIntegerSetGet(ctx, 2, 1, 2, constraints, flags);
1677 // CHECK: (d0, d1)[s0] : (
1678 // CHECK-DAG: d0 - s0 == 0
1679 // CHECK-DAG: d1 - 42 >= 0
1680 mlirIntegerSetDump(set);
1682 // Transform d1 into s0.
1683 MlirAffineExpr s1 = mlirAffineSymbolExprGet(ctx, 1);
1684 MlirAffineExpr repl[] = {d0, s1};
1685 MlirIntegerSet replaced = mlirIntegerSetReplaceGet(set, repl, &s0, 1, 2);
1686 // CHECK: (d0)[s0, s1] : (
1687 // CHECK-DAG: d0 - s0 == 0
1688 // CHECK-DAG: s1 - 42 >= 0
1689 mlirIntegerSetDump(replaced);
1691 if (mlirIntegerSetGetNumDims(set) != 2)
1692 return 3;
1693 if (mlirIntegerSetGetNumDims(replaced) != 1)
1694 return 4;
1696 if (mlirIntegerSetGetNumSymbols(set) != 1)
1697 return 5;
1698 if (mlirIntegerSetGetNumSymbols(replaced) != 2)
1699 return 6;
1701 if (mlirIntegerSetGetNumInputs(set) != 3)
1702 return 7;
1704 if (mlirIntegerSetGetNumConstraints(set) != 2)
1705 return 8;
1707 if (mlirIntegerSetGetNumEqualities(set) != 1)
1708 return 9;
1710 if (mlirIntegerSetGetNumInequalities(set) != 1)
1711 return 10;
1713 MlirAffineExpr cstr1 = mlirIntegerSetGetConstraint(set, 0);
1714 MlirAffineExpr cstr2 = mlirIntegerSetGetConstraint(set, 1);
1715 bool isEq1 = mlirIntegerSetIsConstraintEq(set, 0);
1716 bool isEq2 = mlirIntegerSetIsConstraintEq(set, 1);
1717 if (!mlirAffineExprEqual(cstr1, isEq1 ? d0minusS0 : d1minus42))
1718 return 11;
1719 if (!mlirAffineExprEqual(cstr2, isEq2 ? d0minusS0 : d1minus42))
1720 return 12;
1722 return 0;
1725 int registerOnlyStd(void) {
1726 MlirContext ctx = mlirContextCreate();
1727 // The built-in dialect is always loaded.
1728 if (mlirContextGetNumLoadedDialects(ctx) != 1)
1729 return 1;
1731 MlirDialectHandle stdHandle = mlirGetDialectHandle__func__();
1733 MlirDialect std = mlirContextGetOrLoadDialect(
1734 ctx, mlirDialectHandleGetNamespace(stdHandle));
1735 if (!mlirDialectIsNull(std))
1736 return 2;
1738 mlirDialectHandleRegisterDialect(stdHandle, ctx);
1740 std = mlirContextGetOrLoadDialect(ctx,
1741 mlirDialectHandleGetNamespace(stdHandle));
1742 if (mlirDialectIsNull(std))
1743 return 3;
1745 MlirDialect alsoStd = mlirDialectHandleLoadDialect(stdHandle, ctx);
1746 if (!mlirDialectEqual(std, alsoStd))
1747 return 4;
1749 MlirStringRef stdNs = mlirDialectGetNamespace(std);
1750 MlirStringRef alsoStdNs = mlirDialectHandleGetNamespace(stdHandle);
1751 if (stdNs.length != alsoStdNs.length ||
1752 strncmp(stdNs.data, alsoStdNs.data, stdNs.length))
1753 return 5;
1755 fprintf(stderr, "@registration\n");
1756 // CHECK-LABEL: @registration
1758 // CHECK: func.call is_registered: 1
1759 fprintf(stderr, "func.call is_registered: %d\n",
1760 mlirContextIsRegisteredOperation(
1761 ctx, mlirStringRefCreateFromCString("func.call")));
1763 // CHECK: func.not_existing_op is_registered: 0
1764 fprintf(stderr, "func.not_existing_op is_registered: %d\n",
1765 mlirContextIsRegisteredOperation(
1766 ctx, mlirStringRefCreateFromCString("func.not_existing_op")));
1768 // CHECK: not_existing_dialect.not_existing_op is_registered: 0
1769 fprintf(stderr, "not_existing_dialect.not_existing_op is_registered: %d\n",
1770 mlirContextIsRegisteredOperation(
1771 ctx, mlirStringRefCreateFromCString(
1772 "not_existing_dialect.not_existing_op")));
1774 mlirContextDestroy(ctx);
1775 return 0;
1778 /// Tests backreference APIs
1779 static int testBackreferences(void) {
1780 fprintf(stderr, "@test_backreferences\n");
1782 MlirContext ctx = mlirContextCreate();
1783 mlirContextSetAllowUnregisteredDialects(ctx, true);
1784 MlirLocation loc = mlirLocationUnknownGet(ctx);
1786 MlirOperationState opState =
1787 mlirOperationStateGet(mlirStringRefCreateFromCString("invalid.op"), loc);
1788 MlirRegion region = mlirRegionCreate();
1789 MlirBlock block = mlirBlockCreate(0, NULL, NULL);
1790 mlirRegionAppendOwnedBlock(region, block);
1791 mlirOperationStateAddOwnedRegions(&opState, 1, &region);
1792 MlirOperation op = mlirOperationCreate(&opState);
1793 MlirIdentifier ident =
1794 mlirIdentifierGet(ctx, mlirStringRefCreateFromCString("identifier"));
1796 if (!mlirContextEqual(ctx, mlirOperationGetContext(op))) {
1797 fprintf(stderr, "ERROR: Getting context from operation failed\n");
1798 return 1;
1800 if (!mlirOperationEqual(op, mlirBlockGetParentOperation(block))) {
1801 fprintf(stderr, "ERROR: Getting parent operation from block failed\n");
1802 return 2;
1804 if (!mlirContextEqual(ctx, mlirIdentifierGetContext(ident))) {
1805 fprintf(stderr, "ERROR: Getting context from identifier failed\n");
1806 return 3;
1809 mlirOperationDestroy(op);
1810 mlirContextDestroy(ctx);
1812 // CHECK-LABEL: @test_backreferences
1813 return 0;
1816 /// Tests operand APIs.
1817 int testOperands(void) {
1818 fprintf(stderr, "@testOperands\n");
1819 // CHECK-LABEL: @testOperands
1821 MlirContext ctx = mlirContextCreate();
1822 registerAllUpstreamDialects(ctx);
1824 mlirContextGetOrLoadDialect(ctx, mlirStringRefCreateFromCString("arith"));
1825 mlirContextGetOrLoadDialect(ctx, mlirStringRefCreateFromCString("test"));
1826 MlirLocation loc = mlirLocationUnknownGet(ctx);
1827 MlirType indexType = mlirIndexTypeGet(ctx);
1829 // Create some constants to use as operands.
1830 MlirAttribute indexZeroLiteral =
1831 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("0 : index"));
1832 MlirNamedAttribute indexZeroValueAttr = mlirNamedAttributeGet(
1833 mlirIdentifierGet(ctx, mlirStringRefCreateFromCString("value")),
1834 indexZeroLiteral);
1835 MlirOperationState constZeroState = mlirOperationStateGet(
1836 mlirStringRefCreateFromCString("arith.constant"), loc);
1837 mlirOperationStateAddResults(&constZeroState, 1, &indexType);
1838 mlirOperationStateAddAttributes(&constZeroState, 1, &indexZeroValueAttr);
1839 MlirOperation constZero = mlirOperationCreate(&constZeroState);
1840 MlirValue constZeroValue = mlirOperationGetResult(constZero, 0);
1842 MlirAttribute indexOneLiteral =
1843 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("1 : index"));
1844 MlirNamedAttribute indexOneValueAttr = mlirNamedAttributeGet(
1845 mlirIdentifierGet(ctx, mlirStringRefCreateFromCString("value")),
1846 indexOneLiteral);
1847 MlirOperationState constOneState = mlirOperationStateGet(
1848 mlirStringRefCreateFromCString("arith.constant"), loc);
1849 mlirOperationStateAddResults(&constOneState, 1, &indexType);
1850 mlirOperationStateAddAttributes(&constOneState, 1, &indexOneValueAttr);
1851 MlirOperation constOne = mlirOperationCreate(&constOneState);
1852 MlirValue constOneValue = mlirOperationGetResult(constOne, 0);
1854 // Create the operation under test.
1855 mlirContextSetAllowUnregisteredDialects(ctx, true);
1856 MlirOperationState opState =
1857 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op"), loc);
1858 MlirValue initialOperands[] = {constZeroValue};
1859 mlirOperationStateAddOperands(&opState, 1, initialOperands);
1860 MlirOperation op = mlirOperationCreate(&opState);
1862 // Test operand APIs.
1863 intptr_t numOperands = mlirOperationGetNumOperands(op);
1864 fprintf(stderr, "Num Operands: %" PRIdPTR "\n", numOperands);
1865 // CHECK: Num Operands: 1
1867 MlirValue opOperand1 = mlirOperationGetOperand(op, 0);
1868 fprintf(stderr, "Original operand: ");
1869 mlirValuePrint(opOperand1, printToStderr, NULL);
1870 // CHECK: Original operand: {{.+}} arith.constant 0 : index
1872 mlirOperationSetOperand(op, 0, constOneValue);
1873 MlirValue opOperand2 = mlirOperationGetOperand(op, 0);
1874 fprintf(stderr, "Updated operand: ");
1875 mlirValuePrint(opOperand2, printToStderr, NULL);
1876 // CHECK: Updated operand: {{.+}} arith.constant 1 : index
1878 // Test op operand APIs.
1879 MlirOpOperand use1 = mlirValueGetFirstUse(opOperand1);
1880 if (!mlirOpOperandIsNull(use1)) {
1881 fprintf(stderr, "ERROR: Use should be null\n");
1882 return 1;
1885 MlirOpOperand use2 = mlirValueGetFirstUse(opOperand2);
1886 if (mlirOpOperandIsNull(use2)) {
1887 fprintf(stderr, "ERROR: Use should not be null\n");
1888 return 2;
1891 fprintf(stderr, "Use owner: ");
1892 mlirOperationPrint(mlirOpOperandGetOwner(use2), printToStderr, NULL);
1893 fprintf(stderr, "\n");
1894 // CHECK: Use owner: "dummy.op"
1896 fprintf(stderr, "Use operandNumber: %d\n",
1897 mlirOpOperandGetOperandNumber(use2));
1898 // CHECK: Use operandNumber: 0
1900 use2 = mlirOpOperandGetNextUse(use2);
1901 if (!mlirOpOperandIsNull(use2)) {
1902 fprintf(stderr, "ERROR: Next use should be null\n");
1903 return 3;
1906 MlirOperationState op2State =
1907 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op2"), loc);
1908 MlirValue initialOperands2[] = {constOneValue};
1909 mlirOperationStateAddOperands(&op2State, 1, initialOperands2);
1910 MlirOperation op2 = mlirOperationCreate(&op2State);
1912 MlirOpOperand use3 = mlirValueGetFirstUse(constOneValue);
1913 fprintf(stderr, "First use owner: ");
1914 mlirOperationPrint(mlirOpOperandGetOwner(use3), printToStderr, NULL);
1915 fprintf(stderr, "\n");
1916 // CHECK: First use owner: "dummy.op2"
1918 use3 = mlirOpOperandGetNextUse(mlirValueGetFirstUse(constOneValue));
1919 fprintf(stderr, "Second use owner: ");
1920 mlirOperationPrint(mlirOpOperandGetOwner(use3), printToStderr, NULL);
1921 fprintf(stderr, "\n");
1922 // CHECK: Second use owner: "dummy.op"
1924 MlirAttribute indexTwoLiteral =
1925 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("2 : index"));
1926 MlirNamedAttribute indexTwoValueAttr = mlirNamedAttributeGet(
1927 mlirIdentifierGet(ctx, mlirStringRefCreateFromCString("value")),
1928 indexTwoLiteral);
1929 MlirOperationState constTwoState = mlirOperationStateGet(
1930 mlirStringRefCreateFromCString("arith.constant"), loc);
1931 mlirOperationStateAddResults(&constTwoState, 1, &indexType);
1932 mlirOperationStateAddAttributes(&constTwoState, 1, &indexTwoValueAttr);
1933 MlirOperation constTwo = mlirOperationCreate(&constTwoState);
1934 MlirValue constTwoValue = mlirOperationGetResult(constTwo, 0);
1936 mlirValueReplaceAllUsesOfWith(constOneValue, constTwoValue);
1938 use3 = mlirValueGetFirstUse(constOneValue);
1939 if (!mlirOpOperandIsNull(use3)) {
1940 fprintf(stderr, "ERROR: Use should be null\n");
1941 return 4;
1944 MlirOpOperand use4 = mlirValueGetFirstUse(constTwoValue);
1945 fprintf(stderr, "First replacement use owner: ");
1946 mlirOperationPrint(mlirOpOperandGetOwner(use4), printToStderr, NULL);
1947 fprintf(stderr, "\n");
1948 // CHECK: First replacement use owner: "dummy.op"
1950 use4 = mlirOpOperandGetNextUse(mlirValueGetFirstUse(constTwoValue));
1951 fprintf(stderr, "Second replacement use owner: ");
1952 mlirOperationPrint(mlirOpOperandGetOwner(use4), printToStderr, NULL);
1953 fprintf(stderr, "\n");
1954 // CHECK: Second replacement use owner: "dummy.op2"
1956 mlirOperationDestroy(op);
1957 mlirOperationDestroy(op2);
1958 mlirOperationDestroy(constZero);
1959 mlirOperationDestroy(constOne);
1960 mlirOperationDestroy(constTwo);
1961 mlirContextDestroy(ctx);
1963 return 0;
1966 /// Tests clone APIs.
1967 int testClone(void) {
1968 fprintf(stderr, "@testClone\n");
1969 // CHECK-LABEL: @testClone
1971 MlirContext ctx = mlirContextCreate();
1972 registerAllUpstreamDialects(ctx);
1974 mlirContextGetOrLoadDialect(ctx, mlirStringRefCreateFromCString("func"));
1975 mlirContextGetOrLoadDialect(ctx, mlirStringRefCreateFromCString("arith"));
1976 MlirLocation loc = mlirLocationUnknownGet(ctx);
1977 MlirType indexType = mlirIndexTypeGet(ctx);
1978 MlirStringRef valueStringRef = mlirStringRefCreateFromCString("value");
1980 MlirAttribute indexZeroLiteral =
1981 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("0 : index"));
1982 MlirNamedAttribute indexZeroValueAttr = mlirNamedAttributeGet(
1983 mlirIdentifierGet(ctx, valueStringRef), indexZeroLiteral);
1984 MlirOperationState constZeroState = mlirOperationStateGet(
1985 mlirStringRefCreateFromCString("arith.constant"), loc);
1986 mlirOperationStateAddResults(&constZeroState, 1, &indexType);
1987 mlirOperationStateAddAttributes(&constZeroState, 1, &indexZeroValueAttr);
1988 MlirOperation constZero = mlirOperationCreate(&constZeroState);
1990 MlirAttribute indexOneLiteral =
1991 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("1 : index"));
1992 MlirOperation constOne = mlirOperationClone(constZero);
1993 mlirOperationSetAttributeByName(constOne, valueStringRef, indexOneLiteral);
1995 mlirOperationPrint(constZero, printToStderr, NULL);
1996 mlirOperationPrint(constOne, printToStderr, NULL);
1997 // CHECK: arith.constant 0 : index
1998 // CHECK: arith.constant 1 : index
2000 mlirOperationDestroy(constZero);
2001 mlirOperationDestroy(constOne);
2002 mlirContextDestroy(ctx);
2003 return 0;
2006 // Wraps a diagnostic into additional text we can match against.
2007 MlirLogicalResult errorHandler(MlirDiagnostic diagnostic, void *userData) {
2008 fprintf(stderr, "processing diagnostic (userData: %" PRIdPTR ") <<\n",
2009 (intptr_t)userData);
2010 mlirDiagnosticPrint(diagnostic, printToStderr, NULL);
2011 fprintf(stderr, "\n");
2012 MlirLocation loc = mlirDiagnosticGetLocation(diagnostic);
2013 mlirLocationPrint(loc, printToStderr, NULL);
2014 assert(mlirDiagnosticGetNumNotes(diagnostic) == 0);
2015 fprintf(stderr, "\n>> end of diagnostic (userData: %" PRIdPTR ")\n",
2016 (intptr_t)userData);
2017 return mlirLogicalResultSuccess();
2020 // Logs when the delete user data callback is called
2021 static void deleteUserData(void *userData) {
2022 fprintf(stderr, "deleting user data (userData: %" PRIdPTR ")\n",
2023 (intptr_t)userData);
2026 int testTypeID(MlirContext ctx) {
2027 fprintf(stderr, "@testTypeID\n");
2029 // Test getting and comparing type and attribute type ids.
2030 MlirType i32 = mlirIntegerTypeGet(ctx, 32);
2031 MlirTypeID i32ID = mlirTypeGetTypeID(i32);
2032 MlirType ui32 = mlirIntegerTypeUnsignedGet(ctx, 32);
2033 MlirTypeID ui32ID = mlirTypeGetTypeID(ui32);
2034 MlirType f32 = mlirF32TypeGet(ctx);
2035 MlirTypeID f32ID = mlirTypeGetTypeID(f32);
2036 MlirAttribute i32Attr = mlirIntegerAttrGet(i32, 1);
2037 MlirTypeID i32AttrID = mlirAttributeGetTypeID(i32Attr);
2039 if (mlirTypeIDIsNull(i32ID) || mlirTypeIDIsNull(ui32ID) ||
2040 mlirTypeIDIsNull(f32ID) || mlirTypeIDIsNull(i32AttrID)) {
2041 fprintf(stderr, "ERROR: Expected type ids to be present\n");
2042 return 1;
2045 if (!mlirTypeIDEqual(i32ID, ui32ID) ||
2046 mlirTypeIDHashValue(i32ID) != mlirTypeIDHashValue(ui32ID)) {
2047 fprintf(
2048 stderr,
2049 "ERROR: Expected different integer types to have the same type id\n");
2050 return 2;
2053 if (mlirTypeIDEqual(i32ID, f32ID)) {
2054 fprintf(stderr,
2055 "ERROR: Expected integer type id to not equal float type id\n");
2056 return 3;
2059 if (mlirTypeIDEqual(i32ID, i32AttrID)) {
2060 fprintf(stderr, "ERROR: Expected integer type id to not equal integer "
2061 "attribute type id\n");
2062 return 4;
2065 MlirLocation loc = mlirLocationUnknownGet(ctx);
2066 MlirType indexType = mlirIndexTypeGet(ctx);
2067 MlirStringRef valueStringRef = mlirStringRefCreateFromCString("value");
2069 // Create a registered operation, which should have a type id.
2070 MlirAttribute indexZeroLiteral =
2071 mlirAttributeParseGet(ctx, mlirStringRefCreateFromCString("0 : index"));
2072 MlirNamedAttribute indexZeroValueAttr = mlirNamedAttributeGet(
2073 mlirIdentifierGet(ctx, valueStringRef), indexZeroLiteral);
2074 MlirOperationState constZeroState = mlirOperationStateGet(
2075 mlirStringRefCreateFromCString("arith.constant"), loc);
2076 mlirOperationStateAddResults(&constZeroState, 1, &indexType);
2077 mlirOperationStateAddAttributes(&constZeroState, 1, &indexZeroValueAttr);
2078 MlirOperation constZero = mlirOperationCreate(&constZeroState);
2080 if (!mlirOperationVerify(constZero)) {
2081 fprintf(stderr, "ERROR: Expected operation to verify correctly\n");
2082 return 5;
2085 if (mlirOperationIsNull(constZero)) {
2086 fprintf(stderr, "ERROR: Expected registered operation to be present\n");
2087 return 6;
2090 MlirTypeID registeredOpID = mlirOperationGetTypeID(constZero);
2092 if (mlirTypeIDIsNull(registeredOpID)) {
2093 fprintf(stderr,
2094 "ERROR: Expected registered operation type id to be present\n");
2095 return 7;
2098 // Create an unregistered operation, which should not have a type id.
2099 mlirContextSetAllowUnregisteredDialects(ctx, true);
2100 MlirOperationState opState =
2101 mlirOperationStateGet(mlirStringRefCreateFromCString("dummy.op"), loc);
2102 MlirOperation unregisteredOp = mlirOperationCreate(&opState);
2103 if (mlirOperationIsNull(unregisteredOp)) {
2104 fprintf(stderr, "ERROR: Expected unregistered operation to be present\n");
2105 return 8;
2108 MlirTypeID unregisteredOpID = mlirOperationGetTypeID(unregisteredOp);
2110 if (!mlirTypeIDIsNull(unregisteredOpID)) {
2111 fprintf(stderr,
2112 "ERROR: Expected unregistered operation type id to be null\n");
2113 return 9;
2116 mlirOperationDestroy(constZero);
2117 mlirOperationDestroy(unregisteredOp);
2119 return 0;
2122 int testSymbolTable(MlirContext ctx) {
2123 fprintf(stderr, "@testSymbolTable\n");
2125 const char *moduleString = "func.func private @foo()"
2126 "func.func private @bar()";
2127 const char *otherModuleString = "func.func private @qux()"
2128 "func.func private @foo()";
2130 MlirModule module =
2131 mlirModuleCreateParse(ctx, mlirStringRefCreateFromCString(moduleString));
2132 MlirModule otherModule = mlirModuleCreateParse(
2133 ctx, mlirStringRefCreateFromCString(otherModuleString));
2135 MlirSymbolTable symbolTable =
2136 mlirSymbolTableCreate(mlirModuleGetOperation(module));
2138 MlirOperation funcFoo =
2139 mlirSymbolTableLookup(symbolTable, mlirStringRefCreateFromCString("foo"));
2140 if (mlirOperationIsNull(funcFoo))
2141 return 1;
2143 MlirOperation funcBar =
2144 mlirSymbolTableLookup(symbolTable, mlirStringRefCreateFromCString("bar"));
2145 if (mlirOperationEqual(funcFoo, funcBar))
2146 return 2;
2148 MlirOperation missing =
2149 mlirSymbolTableLookup(symbolTable, mlirStringRefCreateFromCString("qux"));
2150 if (!mlirOperationIsNull(missing))
2151 return 3;
2153 MlirBlock moduleBody = mlirModuleGetBody(module);
2154 MlirBlock otherModuleBody = mlirModuleGetBody(otherModule);
2155 MlirOperation operation = mlirBlockGetFirstOperation(otherModuleBody);
2156 mlirOperationRemoveFromParent(operation);
2157 mlirBlockAppendOwnedOperation(moduleBody, operation);
2159 // At this moment, the operation is still missing from the symbol table.
2160 MlirOperation stillMissing =
2161 mlirSymbolTableLookup(symbolTable, mlirStringRefCreateFromCString("qux"));
2162 if (!mlirOperationIsNull(stillMissing))
2163 return 4;
2165 // After it is added to the symbol table, and not only the operation with
2166 // which the table is associated, it can be looked up.
2167 mlirSymbolTableInsert(symbolTable, operation);
2168 MlirOperation funcQux =
2169 mlirSymbolTableLookup(symbolTable, mlirStringRefCreateFromCString("qux"));
2170 if (!mlirOperationEqual(operation, funcQux))
2171 return 5;
2173 // Erasing from the symbol table also removes the operation.
2174 mlirSymbolTableErase(symbolTable, funcBar);
2175 MlirOperation nowMissing =
2176 mlirSymbolTableLookup(symbolTable, mlirStringRefCreateFromCString("bar"));
2177 if (!mlirOperationIsNull(nowMissing))
2178 return 6;
2180 // Adding a symbol with the same name to the table should rename.
2181 MlirOperation duplicateNameOp = mlirBlockGetFirstOperation(otherModuleBody);
2182 mlirOperationRemoveFromParent(duplicateNameOp);
2183 mlirBlockAppendOwnedOperation(moduleBody, duplicateNameOp);
2184 MlirAttribute newName = mlirSymbolTableInsert(symbolTable, duplicateNameOp);
2185 MlirStringRef newNameStr = mlirStringAttrGetValue(newName);
2186 if (mlirStringRefEqual(newNameStr, mlirStringRefCreateFromCString("foo")))
2187 return 7;
2188 MlirAttribute updatedName = mlirOperationGetAttributeByName(
2189 duplicateNameOp, mlirSymbolTableGetSymbolAttributeName());
2190 if (!mlirAttributeEqual(updatedName, newName))
2191 return 8;
2193 mlirOperationDump(mlirModuleGetOperation(module));
2194 mlirOperationDump(mlirModuleGetOperation(otherModule));
2195 // clang-format off
2196 // CHECK-LABEL: @testSymbolTable
2197 // CHECK: module
2198 // CHECK: func private @foo
2199 // CHECK: func private @qux
2200 // CHECK: func private @foo{{.+}}
2201 // CHECK: module
2202 // CHECK-NOT: @qux
2203 // CHECK-NOT: @foo
2204 // clang-format on
2206 mlirSymbolTableDestroy(symbolTable);
2207 mlirModuleDestroy(module);
2208 mlirModuleDestroy(otherModule);
2210 return 0;
2213 typedef struct {
2214 const char *x;
2215 } callBackData;
2217 void walkCallBack(MlirOperation op, void *rootOpVoid) {
2218 fprintf(stderr, "%s: %s\n", ((callBackData *)(rootOpVoid))->x,
2219 mlirIdentifierStr(mlirOperationGetName(op)).data);
2222 int testOperationWalk(MlirContext ctx) {
2223 // CHECK-LABEL: @testOperationWalk
2224 fprintf(stderr, "@testOperationWalk\n");
2226 const char *moduleString = "module {\n"
2227 " func.func @foo() {\n"
2228 " %1 = arith.constant 10: i32\n"
2229 " arith.addi %1, %1: i32\n"
2230 " return\n"
2231 " }\n"
2232 "}";
2233 MlirModule module =
2234 mlirModuleCreateParse(ctx, mlirStringRefCreateFromCString(moduleString));
2236 callBackData data;
2237 data.x = "i love you";
2239 // CHECK: i love you: arith.constant
2240 // CHECK: i love you: arith.addi
2241 // CHECK: i love you: func.return
2242 // CHECK: i love you: func.func
2243 // CHECK: i love you: builtin.module
2244 mlirOperationWalk(mlirModuleGetOperation(module), walkCallBack,
2245 (void *)(&data), MlirWalkPostOrder);
2247 data.x = "i don't love you";
2248 // CHECK: i don't love you: builtin.module
2249 // CHECK: i don't love you: func.func
2250 // CHECK: i don't love you: arith.constant
2251 // CHECK: i don't love you: arith.addi
2252 // CHECK: i don't love you: func.return
2253 mlirOperationWalk(mlirModuleGetOperation(module), walkCallBack,
2254 (void *)(&data), MlirWalkPreOrder);
2255 mlirModuleDestroy(module);
2256 return 0;
2259 int testDialectRegistry(void) {
2260 fprintf(stderr, "@testDialectRegistry\n");
2262 MlirDialectRegistry registry = mlirDialectRegistryCreate();
2263 if (mlirDialectRegistryIsNull(registry)) {
2264 fprintf(stderr, "ERROR: Expected registry to be present\n");
2265 return 1;
2268 MlirDialectHandle stdHandle = mlirGetDialectHandle__func__();
2269 mlirDialectHandleInsertDialect(stdHandle, registry);
2271 MlirContext ctx = mlirContextCreate();
2272 if (mlirContextGetNumRegisteredDialects(ctx) != 0) {
2273 fprintf(stderr,
2274 "ERROR: Expected no dialects to be registered to new context\n");
2277 mlirContextAppendDialectRegistry(ctx, registry);
2278 if (mlirContextGetNumRegisteredDialects(ctx) != 1) {
2279 fprintf(stderr, "ERROR: Expected the dialect in the registry to be "
2280 "registered to the context\n");
2283 mlirContextDestroy(ctx);
2284 mlirDialectRegistryDestroy(registry);
2286 return 0;
2289 void testExplicitThreadPools(void) {
2290 MlirLlvmThreadPool threadPool = mlirLlvmThreadPoolCreate();
2291 MlirDialectRegistry registry = mlirDialectRegistryCreate();
2292 mlirRegisterAllDialects(registry);
2293 MlirContext context =
2294 mlirContextCreateWithRegistry(registry, /*threadingEnabled=*/false);
2295 mlirContextSetThreadPool(context, threadPool);
2296 mlirContextDestroy(context);
2297 mlirDialectRegistryDestroy(registry);
2298 mlirLlvmThreadPoolDestroy(threadPool);
2301 void testDiagnostics(void) {
2302 MlirContext ctx = mlirContextCreate();
2303 MlirDiagnosticHandlerID id = mlirContextAttachDiagnosticHandler(
2304 ctx, errorHandler, (void *)42, deleteUserData);
2305 fprintf(stderr, "@test_diagnostics\n");
2306 MlirLocation unknownLoc = mlirLocationUnknownGet(ctx);
2307 mlirEmitError(unknownLoc, "test diagnostics");
2308 MlirAttribute unknownAttr = mlirLocationGetAttribute(unknownLoc);
2309 MlirLocation unknownClone = mlirLocationFromAttribute(unknownAttr);
2310 mlirEmitError(unknownClone, "test clone");
2311 MlirLocation fileLineColLoc = mlirLocationFileLineColGet(
2312 ctx, mlirStringRefCreateFromCString("file.c"), 1, 2);
2313 mlirEmitError(fileLineColLoc, "test diagnostics");
2314 MlirLocation callSiteLoc = mlirLocationCallSiteGet(
2315 mlirLocationFileLineColGet(
2316 ctx, mlirStringRefCreateFromCString("other-file.c"), 2, 3),
2317 fileLineColLoc);
2318 mlirEmitError(callSiteLoc, "test diagnostics");
2319 MlirLocation null = {0};
2320 MlirLocation nameLoc =
2321 mlirLocationNameGet(ctx, mlirStringRefCreateFromCString("named"), null);
2322 mlirEmitError(nameLoc, "test diagnostics");
2323 MlirLocation locs[2] = {nameLoc, callSiteLoc};
2324 MlirAttribute nullAttr = {0};
2325 MlirLocation fusedLoc = mlirLocationFusedGet(ctx, 2, locs, nullAttr);
2326 mlirEmitError(fusedLoc, "test diagnostics");
2327 mlirContextDetachDiagnosticHandler(ctx, id);
2328 mlirEmitError(unknownLoc, "more test diagnostics");
2329 // CHECK-LABEL: @test_diagnostics
2330 // CHECK: processing diagnostic (userData: 42) <<
2331 // CHECK: test diagnostics
2332 // CHECK: loc(unknown)
2333 // CHECK: processing diagnostic (userData: 42) <<
2334 // CHECK: test clone
2335 // CHECK: loc(unknown)
2336 // CHECK: >> end of diagnostic (userData: 42)
2337 // CHECK: processing diagnostic (userData: 42) <<
2338 // CHECK: test diagnostics
2339 // CHECK: loc("file.c":1:2)
2340 // CHECK: >> end of diagnostic (userData: 42)
2341 // CHECK: processing diagnostic (userData: 42) <<
2342 // CHECK: test diagnostics
2343 // CHECK: loc(callsite("other-file.c":2:3 at "file.c":1:2))
2344 // CHECK: >> end of diagnostic (userData: 42)
2345 // CHECK: processing diagnostic (userData: 42) <<
2346 // CHECK: test diagnostics
2347 // CHECK: loc("named")
2348 // CHECK: >> end of diagnostic (userData: 42)
2349 // CHECK: processing diagnostic (userData: 42) <<
2350 // CHECK: test diagnostics
2351 // CHECK: loc(fused["named", callsite("other-file.c":2:3 at "file.c":1:2)])
2352 // CHECK: deleting user data (userData: 42)
2353 // CHECK-NOT: processing diagnostic
2354 // CHECK: more test diagnostics
2355 mlirContextDestroy(ctx);
2358 int main(void) {
2359 MlirContext ctx = mlirContextCreate();
2360 registerAllUpstreamDialects(ctx);
2361 mlirContextGetOrLoadDialect(ctx, mlirStringRefCreateFromCString("func"));
2362 mlirContextGetOrLoadDialect(ctx, mlirStringRefCreateFromCString("memref"));
2363 mlirContextGetOrLoadDialect(ctx, mlirStringRefCreateFromCString("shape"));
2364 mlirContextGetOrLoadDialect(ctx, mlirStringRefCreateFromCString("scf"));
2366 if (constructAndTraverseIr(ctx))
2367 return 1;
2368 buildWithInsertionsAndPrint(ctx);
2369 if (createOperationWithTypeInference(ctx))
2370 return 2;
2372 if (printBuiltinTypes(ctx))
2373 return 3;
2374 if (printBuiltinAttributes(ctx))
2375 return 4;
2376 if (printAffineMap(ctx))
2377 return 5;
2378 if (printAffineExpr(ctx))
2379 return 6;
2380 if (affineMapFromExprs(ctx))
2381 return 7;
2382 if (printIntegerSet(ctx))
2383 return 8;
2384 if (registerOnlyStd())
2385 return 9;
2386 if (testBackreferences())
2387 return 10;
2388 if (testOperands())
2389 return 11;
2390 if (testClone())
2391 return 12;
2392 if (testTypeID(ctx))
2393 return 13;
2394 if (testSymbolTable(ctx))
2395 return 14;
2396 if (testDialectRegistry())
2397 return 15;
2398 if (testOperationWalk(ctx))
2399 return 16;
2401 testExplicitThreadPools();
2402 testDiagnostics();
2404 // CHECK: DESTROY MAIN CONTEXT
2405 // CHECK: reportResourceDelete: resource_i64_blob
2406 fprintf(stderr, "DESTROY MAIN CONTEXT\n");
2407 mlirContextDestroy(ctx);
2409 return 0;