summaryrefslogtreecommitdiffstats
path: root/mlir/lib
Commit message (Collapse)AuthorAgeFilesLines
...
* Lower linalg.copy to LLVM dialect in the presence of transposes.Nicolas Vasilache2019-08-231-13/+63
| | | | | | | | | | Add an extra RewritePattern that does not convert types to rewrite a CopyOp that has non-identity permutations into a sequence of TransposeOp followed by a CopyOp without such permutations. This RewitePattern is made to fail in the non-permutation case so that the conversion pattern can kick in to lower to LLVM. This is an instance of A->A->B lowering where A->A is done by a RewritePattern in case_1 and A->B is done by a ConversionPatternRewriter when not(case_1). PiperOrigin-RevId: 265171380
* Lower linalg.transpose to LLVM dialectNicolas Vasilache2019-08-231-3/+112
| | | | | | | | | | | | Add a conversion pattern that transforms a linalg.transpose op into: 1. A function entry `alloca` operation to allocate a ViewDescriptor. 2. A load of the ViewDescriptor from the pointer allocated in 1. 3. Updates to the ViewDescriptor to introduce the data ptr, offset, size and stride. Size and stride are permutations of the original values. 4. A store of the resulting ViewDescriptor to the alloca'ed pointer. The linalg.transpose op is replaced by the alloca'ed pointer. PiperOrigin-RevId: 265169112
* Add a linalg.transpose opNicolas Vasilache2019-08-231-2/+35
| | | | | | | | | | | | | | A linalg.transpose op is a pure metadata operation that takes a view + permutation map and produces another view of the same underlying data, with a different reindexing. This is a pure metadata operation that does not touch the underlying data. Example: ``` %t = linalg.transpose %v (i, j) -> (j, i) : !linalg.view<?x?xf32> ``` PiperOrigin-RevId: 265139429
* NFC: Add a note to 'applyPatternsGreedily' that it also performs folding/dce.River Riddle2019-08-231-3/+2
| | | | | | Fixes tensorflow/mlir#72 PiperOrigin-RevId: 265097597
* Add lowering of linalg.copy to an external C++ library and a test.Nicolas Vasilache2019-08-231-8/+19
| | | | | | This CL extends support for lowering of linalg to external C++ libraries with CopyOp. Currently this can only work when the permutation maps in the copies are identity. Future support for permutations will be added later. PiperOrigin-RevId: 265093025
* [spirv] NFC: move SPIR-V control flow ops to a separate fileLei Zhang2019-08-231-7/+7
| | | | | | This CL is also purely moving code around for better file organization. PiperOrigin-RevId: 265092566
* Introduce the ability for "isolated from above" ops to introduce shadowingChris Lattner2019-08-231-7/+54
| | | | | | names for the basic block arguments in their body. PiperOrigin-RevId: 265084627
* NFC: Update in-code documentation. Make the two grammar definitions of ↵MLIR Team2019-08-231-3/+5
| | | | | | static-dimension-list consistent. PiperOrigin-RevId: 265084348
* Add iterator support to ElementsAttr and SparseElementsAttr.River Riddle2019-08-222-30/+73
| | | | | | This will allow iterating the values of a non-opaque ElementsAttr, with all of the types currently supported by DenseElementsAttr. This should help reduce the amount of specialization on DenseElementsAttr. PiperOrigin-RevId: 264968151
* [spirv] Add support for extension (de)serializationLei Zhang2019-08-223-2/+67
| | | | | | | Only a few important KHR extensions are registered to the SPIR-V dialect for now. PiperOrigin-RevId: 264939428
* Avoid overflow when lowering linalg.sliceNicolas Vasilache2019-08-221-20/+21
| | | | | | | | linalg.subview used to lower to a slice with a bounded range resulting in correct bounded accesses. However linalg.slice could still index out of bounds. This CL moves the bounding to linalg.slice. LLVM select and cmp ops gain a more idiomatic builder. PiperOrigin-RevId: 264897125
* [spirv] Add support for capability (de)serializationLei Zhang2019-08-223-4/+72
| | | | | | | This CL pulls in capabilities defined in the spec and adds support for (de)serialize capabilities of a spv.module. PiperOrigin-RevId: 264877413
* Split out parsing location into separate functions per instanceJacques Pienaar2019-08-221-107/+127
| | | | | | Split out method into specialized instances + add an early exit. Should be NFC, but simplifies reading the logic slightly IMHO. PiperOrigin-RevId: 264855529
* Let LLVMOpLowering specify a PatternBenefit - NFCNicolas Vasilache2019-08-221-3/+3
| | | | | | Currently the benefit is always set to 1 which limits the ability to do A->B->C lowering PiperOrigin-RevId: 264854146
* NFC: Fix path of LinalgLibraryOpInterfaces inc files.River Riddle2019-08-221-1/+1
| | | | PiperOrigin-RevId: 264827908
* Add support for generating operation interfaces from the ODS framework.River Riddle2019-08-211-0/+2
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Operation interfaces generally require a bit of boilerplate code to connect all of the pieces together. This cl introduces mechanisms in the ODS to allow for generating operation interfaces via the 'OpInterface' class. Providing a definition of the `OpInterface` class will auto-generate the c++ classes for the interface. An `OpInterface` includes a name, for the c++ class, along with a list of interface methods. There are two types of methods that can be used with an interface, `InterfaceMethod` and `StaticInterfaceMethod`. They are both comprised of the same core components, with the distinction that `StaticInterfaceMethod` models a static method on the derived operation. An `InterfaceMethod` is comprised of the following components: * ReturnType - A string corresponding to the c++ return type of the method. * MethodName - A string corresponding to the desired name of the method. * Arguments - A dag of strings that correspond to a c++ type and variable name respectively. * MethodBody (Optional) - An optional explicit implementation of the interface method. def MyInterface : OpInterface<"MyInterface"> { let methods = [ // A simple non-static method with no inputs. InterfaceMethod<"unsigned", "foo">, // A new non-static method accepting an input argument. InterfaceMethod<"Value *", "bar", (ins "unsigned":$i)>, // Query a static property of the derived operation. StaticInterfaceMethod<"unsigned", "fooStatic">, // Provide the definition of a static interface method. // Note: `ConcreteOp` corresponds to the derived operation typename. StaticInterfaceMethod<"Operation *", "create", (ins "OpBuilder &":$builder, "Location":$loc), [{ return builder.create<ConcreteOp>(loc); }]>, // Provide a definition of the non-static method. // Note: `op` corresponds to the derived operation variable. InterfaceMethod<"unsigned", "getNumInputsAndOutputs", (ins), [{ return op.getNumInputs() + op.getNumOutputs(); }]>, ]; PiperOrigin-RevId: 264754898
* Avoid assigning to an unchecked Error.River Riddle2019-08-211-10/+14
| | | | | | Fixes tensorflow/mlir#97 PiperOrigin-RevId: 264743395
* Point to spv.AccessChain when reporting spv.AccessChain errorsLei Zhang2019-08-211-2/+1
| | | | PiperOrigin-RevId: 264742130
* Remove dead getLLVMLibraryCallImplDefinition in Linalg's ↵Nicolas Vasilache2019-08-211-27/+4
| | | | | | LowerToLLVMDialect.cpp - NFC PiperOrigin-RevId: 264740014
* Reduce reliance on custom grown Jit implementation - NFCNicolas Vasilache2019-08-212-208/+130
| | | | | | | | | | This CL makes use of the standard LLVM LLJIT and removes the need for a custom JIT implementation within MLIR. To achieve this, one needs to clone (i.e. serde) the produced llvm::Module into a new LLVMContext. This is currently necessary because the llvm::LLVMContext is owned by the LLVMDialect, somewhat deep in the call hierarchy. In the future we should remove the reliance of serding the llvm::Module by allowing the injection of an LLVMContext from the top-level. Unfortunately this will require deeper API changes and impact multiple places. It is therefore left for future work. PiperOrigin-RevId: 264737459
* Remove the wrapping function in SPIR-V (de)serializationLei Zhang2019-08-212-35/+6
| | | | | | | | | Previously Module and Function are builtinn constructs in MLIR. Due to the structural requirements we must wrap the SPIR-V module inside a Function inside a Module. Now the requirement is lifted and we can remove the wrapping function! :) PiperOrigin-RevId: 264736051
* NFC: Update in-code documentation for type.MLIR Team2019-08-211-3/+3
| | | | PiperOrigin-RevId: 264734014
* NFC: Update in-code documentation for function-type.MLIR Team2019-08-211-1/+1
| | | | PiperOrigin-RevId: 264723462
* Add a hook to the OpAsmDialectInterface to allow providing a special name ↵River Riddle2019-08-212-23/+52
| | | | | | | | for the operation result. This generalizes the current special handling for constant operations(they get named 'cst'/'true'/'false'/etc.) PiperOrigin-RevId: 264723379
* Automated rollback of commit b9dc2e481818315f2f0d87455349f497f6118a4cRiver Riddle2019-08-212-73/+30
| | | | PiperOrigin-RevId: 264672975
* NFC: Make the ModuleState field in the ModulePrinter optional.River Riddle2019-08-211-43/+35
| | | | | | The ModuleState is only used for printing aliases, which is only done when printing the top-level module. PiperOrigin-RevId: 264664138
* Add iterator support to ElementsAttr and SparseElementsAttr.River Riddle2019-08-212-30/+73
| | | | | | This will allow iterating the values of a non-opaque ElementsAttr, with all of the types currently supported by DenseElementsAttr. This should help reduce the amount of specialization on DenseElementsAttr. PiperOrigin-RevId: 264637293
* Move the parser extensions for aliases currently on Dialect to a new ↵River Riddle2019-08-212-12/+16
| | | | | | | | OpAsmDialectInterface. This will allow for adding more hooks for controlling parser behavior without bloating Dialect in the common case. This cl also adds iteration support to the DialectInterfaceCollection. PiperOrigin-RevId: 264627846
* [spirv] Support i1 as bool typeLei Zhang2019-08-211-8/+14
| | | | PiperOrigin-RevId: 264612014
* Support variadic ops in declarative rewrite rulesLei Zhang2019-08-211-16/+87
| | | | | | | | | | | | | | | | | | | | | | | | This CL extends declarative rewrite rules to support matching and generating ops with variadic operands/results. For this, the generated `matchAndRewrite()` method for each pattern now are changed to * Use "range" types for the local variables used to store captured values (`operand_range` for operands, `ArrayRef<Value *>` for values, *Op for results). This allows us to have a unified way of handling both single values and value ranges. * Create local variables for each operand for op creation. If the operand is variadic, then a `SmallVector<Value*>` will be created to collect all values for that operand; otherwise a `Value*` will be created. * Use a collective result type builder. All result types are specified via a single parameter to the builder. We can use one result pattern to replace multiple results of the matched root op. When that happens, it will require specifying types for multiple results. Add a new collective-type builder. PiperOrigin-RevId: 264588559
* Materialize spv.constants at use sitesLei Zhang2019-08-211-58/+70
| | | | | | | | | | | | | | | In SPIR-V binary format, constants are placed at the module level and referenced by instructions inside functions using their result <id>s. To model this natively (using SSA values for result <id>s), it means we need to have implicit capturing functions. We will lose the ability to have function passes if going down that path. Instead, this CL changes to materialize constants at their use sites in deserialization. It's cheap to copy constants in MLIR given that attributes is uniqued to MLIRContext. By localizing constants into functions, we can preserve isolated functions. PiperOrigin-RevId: 264582532
* NFC: Keep the dialect list in the context sorted by namespace.River Riddle2019-08-201-6/+14
| | | | | | Most dialects are initialized statically, which does not have a guaranteed initialization order. By keeping the dialect list sorted, we can guarantee a deterministic iteration order of dialects. PiperOrigin-RevId: 264522875
* NFC: Use a DenseSet instead of a DenseMap for DialectInterfaceCollection.River Riddle2019-08-201-2/+2
| | | | | | The interfaces are looked up by dialect, which can always be retrieved from an interface instance. PiperOrigin-RevId: 264516023
* NFC: Move AffineOps dialect to the Dialect sub-directory.River Riddle2019-08-2032-38/+38
| | | | PiperOrigin-RevId: 264482571
* Add spv.specConstant and spv._reference_ofLei Zhang2019-08-203-165/+364
| | | | | | | | | | | | | | | | | | | | | | | | | | | Similar to global variables, specialization constants also live in the module scope and can be referenced by instructions in functions in native SPIR-V. A direct modelling would be to allow functions in the SPIR-V dialect to implicit capture, but it means we are losing the ability to write passes for Functions. While in SPIR-V normally we want to process the module as a whole, it's not common to see multiple functions get used so we'd like to leave the door open for those cases. Therefore, similar to global variables, we introduce spv.specConstant to model three SPIR-V instructions: OpSpecConstantTrue, OpSpecConstantFalse, and OpSpecConstant. They do not return SSA value results; instead they have symbols and can only be referenced by the symbols. To use it in a function, we need to have another op spv._reference_of to turn the symbol into an SSA value. This breaks the tie and makes functions still explicit capture. Previously specialization constants were handled similarly as normal constants. That is incorrect given that specialization constant actually acts more like variable (without need to load and store). E.g., they cannot be de-duplicated like normal constants. This CL also refines various documents and comments. PiperOrigin-RevId: 264455172
* [spirv] Support (de)serialization of spv.structDenis Khalikov2019-08-202-0/+112
| | | | | | | | Support (de)serialization of spv.struct with offset decorations. Closes tensorflow/mlir#94 PiperOrigin-RevId: 264421427
* Fix build of affine load/store with empty mapDiego Caballero2019-08-206-7/+14
| | | | | | | | | | | | | | | tensorflow/mlir#58 fixed and exercised verification of load/store ops using empty affine maps. Unfortunately, it didn't exercise the creation of them. This PR addresses that aspect. It removes the assumption of AffineMap having at least one result and stores a pointer to MLIRContext as member of AffineMap. * Add empty map support to affine.store + test * Move MLIRContext to AffineMapStorage Closes tensorflow/mlir#74 PiperOrigin-RevId: 264416260
* ConvertLaunchFuncToCudaCalls: use LLVM dialect globalsAlex Zinenko2019-08-203-52/+60
| | | | | | | | | | | | This conversion has been using a stack-allocated array of i8 to store the null-terminated kernel name in order to pass it to the CUDA wrappers expecting a C string because the LLVM dialect was missing support for globals. Now that the suport is introduced, use a global instead. Refactor global string construction from GenerateCubinAccessors into a common utility function living in the LLVM namespace. PiperOrigin-RevId: 264382489
* JitRunner: support entry functions returning voidAlex Zinenko2019-08-201-31/+50
| | | | | | | | | | | | | JitRunner can use as entry points functions that produce either a single '!llvm.f32' value or a list of memrefs. Memref support is legacy and was introduced before MLIR could lower memref allocation and deallocation to malloc/free calls so as to allocate the memory externally, and is likely to be dropped in the future since it unconditionally runs affine+standard-to-llvm lowering on the module instead of accepting the LLVM dialect. CUDA runner relies on memref-based flow in the runner without actually returning anything. Introduce a runner flow to use functions that return void as entry points. PiperOrigin-RevId: 264381686
* Add support for LLVM lowering of binary ops on n-D vector typesNicolas Vasilache2019-08-203-27/+138
| | | | | | This CL allows binary operations on n-D vector types to be lowered to LLVMIR by performing an (n-1)-D extractvalue, 1-D vector operation and an (n-1)-D insertvalue. PiperOrigin-RevId: 264339118
* Fix AffineExpr::simplifyAdd bugUday Bondhugula2019-08-201-1/+1
| | | | | | | | | | | | - fix missing check while simplifying an expression with floordiv to a mod - fixes issue tensorflow/mlir#82 Signed-off-by: Uday Bondhugula <uday@polymagelabs.com> Closes tensorflow/mlir#84 PiperOrigin-RevId: 264338353
* Move Linalg and VectorOps dialects to the Dialect subdir - NFCNicolas Vasilache2019-08-1922-54/+54
| | | | PiperOrigin-RevId: 264277760
* Allow isolated regions to form isolated SSA name scopes in the printer.River Riddle2019-08-191-73/+110
| | | | | | | | | | | This will allow for naming values the same as existing SSA values for regions attached to operations that are isolated from above. This fits in with how the system already allows separate name scopes for sibling regions. This name shadowing can be enabled in the custom parser of operations by setting the 'enableNameShadowing' flag to true when calling 'parseRegion'. %arg = constant 10 : i32 foo.op { %arg = constant 10 : i32 } PiperOrigin-RevId: 264255999
* Add alignment support to linalg.buffer_allocNicolas Vasilache2019-08-192-14/+45
| | | | | | | | | | | | | | | | | | | | | | | This CL adds an integer attribute to linalg.buffer_alloc and lowering to LLVM. The alignment is constrained to be a positive power of 2. Lowering to LLVM produces the pattern: ``` %[[alloc:.*]] = llvm.call @malloc(%[[s]]) : (!llvm.i64) -> !llvm<"i8*"> %[[cast:.*]] = llvm.bitcast %[[alloc]] : !llvm<"i8*"> to !llvm.i64 %[[rem:.*]] = llvm.urem %[[cast]], %[[c16]] : !llvm.i64 %[[drem:.*]] = llvm.sub %[[c16]], %[[rem]] : !llvm.i64 %[[off:.*]] = llvm.urem %[[drem]], %[[c16]] : !llvm.i64 llvm.getelementptr %{{.*}}[%[[off]]] : (!llvm<"i8*">, !llvm.i64) -> !llvm<"i8*"> ``` where `ptr` is aligned on `align` by computing the address `ptr + (align - ptr % align) % align`. To allow dealloc op to still be able to free memory, additional information is needed in the buffer type. The buffer type is thus extended with an extra i8* for the base allocation address. PiperOrigin-RevId: 264244455
* Fix parsing/printing of spv.globalVariable and spv._address_ofMahesh Ravishankar2019-08-191-20/+16
| | | | | | | | | | | | Change the prining/parsing of spv.globalVariable to print the type of the variable after the ':' to be consistent with MLIR convention. The spv._address_of should print the variable type after the ':'. It was mistakenly printing the address of the return value. Add a (missing) test that should have caught that. Also move spv.globalVariable and spv._address_of tests to structure-ops.mlir. PiperOrigin-RevId: 264204686
* NFC: Move LLVMIR, SDBM, and StandardOps to the Dialect/ directory.River Riddle2019-08-1961-77/+77
| | | | PiperOrigin-RevId: 264193915
* [spirv] Add spv.ReturnValueLei Zhang2019-08-191-4/+38
| | | | | | | | | This CL adds the spv.ReturnValue op and its tests. Also adds a InFunctionScope trait to make sure that the op stays inside a function. To be consistent, ModuleOnly trait is changed to InModuleScope. PiperOrigin-RevId: 264193081
* Refactor linalg lowering to LLVMNicolas Vasilache2019-08-193-133/+142
| | | | | | | | | | | | | The linalg.view type used to be lowered to a struct containing a data pointer, offset, sizes/strides information. This was problematic when passing to external functions due to ABI, struct padding and alignment issues. The linalg.view type is now lowered to LLVMIR as a *pointer* to a struct containing the data pointer, offset and sizes/strides. This simplifies the interfacing with external library functions and makes it trivial to add new functions without creating a shim that would go from a value type struct to a pointer type. The consequences are that: 1. lowering explicitly uses llvm.alloca in lieu of llvm.undef and performs the proper llvm.load/llvm.store where relevant. 2. the shim creation function `getLLVMLibraryCallDefinition` disappears. 3. views are passed by pointer, scalars are passed by value. In the future, other structs will be passed by pointer (on a per-need basis). PiperOrigin-RevId: 264183671
* Add alignment support for llvm.allocaNicolas Vasilache2019-08-181-1/+4
| | | | | | Extend the LLVM dialect AllocaOp with an alignment attribute. PiperOrigin-RevId: 264068306
* InitLLVM already initializes PrettyStackTraceProgramJacques Pienaar2019-08-181-2/+0
| | | | | | Remove extra PrettyStackTraceProgram and use InitLLVM consistently. PiperOrigin-RevId: 264041205
OpenPOWER on IntegriCloud