1// RUN: mlir-opt %s -split-input-file -verify-diagnostics 2 3func.func @invalid_new_dense(%arg0: !llvm.ptr<i8>) -> tensor<32xf32> { 4 // expected-error@+1 {{'sparse_tensor.new' op result #0 must be sparse tensor of any type values, but got 'tensor<32xf32>'}} 5 %0 = sparse_tensor.new %arg0 : !llvm.ptr<i8> to tensor<32xf32> 6 return %0 : tensor<32xf32> 7} 8 9// ----- 10 11func.func @invalid_pointers_dense(%arg0: tensor<128xf64>) -> memref<?xindex> { 12 %c = arith.constant 0 : index 13 // expected-error@+1 {{'sparse_tensor.pointers' op operand #0 must be sparse tensor of any type values, but got 'tensor<128xf64>'}} 14 %0 = sparse_tensor.pointers %arg0, %c : tensor<128xf64> to memref<?xindex> 15 return %0 : memref<?xindex> 16} 17 18// ----- 19 20func.func @invalid_pointers_unranked(%arg0: tensor<*xf64>) -> memref<?xindex> { 21 %c = arith.constant 0 : index 22 // expected-error@+1 {{'sparse_tensor.pointers' op operand #0 must be sparse tensor of any type values, but got 'tensor<*xf64>'}} 23 %0 = sparse_tensor.pointers %arg0, %c : tensor<*xf64> to memref<?xindex> 24 return %0 : memref<?xindex> 25} 26 27// ----- 28 29#SparseVector = #sparse_tensor.encoding<{dimLevelType = ["compressed"], pointerBitWidth=32}> 30 31func.func @mismatch_pointers_types(%arg0: tensor<128xf64, #SparseVector>) -> memref<?xindex> { 32 %c = arith.constant 0 : index 33 // expected-error@+1 {{unexpected type for pointers}} 34 %0 = sparse_tensor.pointers %arg0, %c : tensor<128xf64, #SparseVector> to memref<?xindex> 35 return %0 : memref<?xindex> 36} 37 38// ----- 39 40#SparseVector = #sparse_tensor.encoding<{dimLevelType = ["compressed"]}> 41 42func.func @pointers_oob(%arg0: tensor<128xf64, #SparseVector>) -> memref<?xindex> { 43 %c = arith.constant 1 : index 44 // expected-error@+1 {{requested pointers dimension out of bounds}} 45 %0 = sparse_tensor.pointers %arg0, %c : tensor<128xf64, #SparseVector> to memref<?xindex> 46 return %0 : memref<?xindex> 47} 48 49// ----- 50 51func.func @invalid_indices_dense(%arg0: tensor<10x10xi32>) -> memref<?xindex> { 52 %c = arith.constant 1 : index 53 // expected-error@+1 {{'sparse_tensor.indices' op operand #0 must be sparse tensor of any type values, but got 'tensor<10x10xi32>'}} 54 %0 = sparse_tensor.indices %arg0, %c : tensor<10x10xi32> to memref<?xindex> 55 return %0 : memref<?xindex> 56} 57 58// ----- 59 60func.func @invalid_indices_unranked(%arg0: tensor<*xf64>) -> memref<?xindex> { 61 %c = arith.constant 0 : index 62 // expected-error@+1 {{'sparse_tensor.indices' op operand #0 must be sparse tensor of any type values, but got 'tensor<*xf64>'}} 63 %0 = sparse_tensor.indices %arg0, %c : tensor<*xf64> to memref<?xindex> 64 return %0 : memref<?xindex> 65} 66 67// ----- 68 69#SparseVector = #sparse_tensor.encoding<{dimLevelType = ["compressed"]}> 70 71func.func @mismatch_indices_types(%arg0: tensor<?xf64, #SparseVector>) -> memref<?xi32> { 72 %c = arith.constant 0 : index 73 // expected-error@+1 {{unexpected type for indices}} 74 %0 = sparse_tensor.indices %arg0, %c : tensor<?xf64, #SparseVector> to memref<?xi32> 75 return %0 : memref<?xi32> 76} 77 78// ----- 79 80#SparseVector = #sparse_tensor.encoding<{dimLevelType = ["compressed"]}> 81 82func.func @indices_oob(%arg0: tensor<128xf64, #SparseVector>) -> memref<?xindex> { 83 %c = arith.constant 1 : index 84 // expected-error@+1 {{requested indices dimension out of bounds}} 85 %0 = sparse_tensor.indices %arg0, %c : tensor<128xf64, #SparseVector> to memref<?xindex> 86 return %0 : memref<?xindex> 87} 88 89// ----- 90 91func.func @invalid_values_dense(%arg0: tensor<1024xf32>) -> memref<?xf32> { 92 // expected-error@+1 {{'sparse_tensor.values' op operand #0 must be sparse tensor of any type values, but got 'tensor<1024xf32>'}} 93 %0 = sparse_tensor.values %arg0 : tensor<1024xf32> to memref<?xf32> 94 return %0 : memref<?xf32> 95} 96 97// ----- 98 99#SparseVector = #sparse_tensor.encoding<{dimLevelType = ["compressed"]}> 100 101func.func @mismatch_values_types(%arg0: tensor<?xf64, #SparseVector>) -> memref<?xf32> { 102 // expected-error@+1 {{unexpected mismatch in element types}} 103 %0 = sparse_tensor.values %arg0 : tensor<?xf64, #SparseVector> to memref<?xf32> 104 return %0 : memref<?xf32> 105} 106 107// ----- 108 109func.func @sparse_unannotated_load(%arg0: tensor<16x32xf64>) -> tensor<16x32xf64> { 110 // expected-error@+1 {{'sparse_tensor.load' op operand #0 must be sparse tensor of any type values, but got 'tensor<16x32xf64>'}} 111 %0 = sparse_tensor.load %arg0 : tensor<16x32xf64> 112 return %0 : tensor<16x32xf64> 113} 114 115// ----- 116 117func.func @sparse_unannotated_insert(%arg0: tensor<128xf64>, %arg1: memref<?xindex>, %arg2: f64) { 118 // expected-error@+1 {{'sparse_tensor.lex_insert' op operand #0 must be sparse tensor of any type values, but got 'tensor<128xf64>'}} 119 sparse_tensor.lex_insert %arg0, %arg1, %arg2 : tensor<128xf64>, memref<?xindex>, f64 120 return 121} 122 123// ----- 124 125func.func @sparse_unannotated_expansion(%arg0: tensor<128xf64>) { 126 // expected-error@+1 {{'sparse_tensor.expand' op operand #0 must be sparse tensor of any type values, but got 'tensor<128xf64>'}} 127 %values, %filled, %added, %count = sparse_tensor.expand %arg0 128 : tensor<128xf64> to memref<?xf64>, memref<?xi1>, memref<?xindex>, index 129 return 130} 131 132// ----- 133 134func.func @sparse_unannotated_compression(%arg0: tensor<128xf64>, %arg1: memref<?xindex>, 135 %arg2: memref<?xf64>, %arg3: memref<?xi1>, 136 %arg4: memref<?xindex>, %arg5: index) { 137 // expected-error@+1 {{'sparse_tensor.compress' op operand #0 must be sparse tensor of any type values, but got 'tensor<128xf64>'}} 138 sparse_tensor.compress %arg0, %arg1, %arg2, %arg3, %arg4, %arg5 139 : tensor<128xf64>, memref<?xindex>, memref<?xf64>, memref<?xi1>, memref<?xindex>, index 140} 141 142// ----- 143 144func.func @sparse_convert_unranked(%arg0: tensor<*xf32>) -> tensor<10xf32> { 145 // expected-error@+1 {{unexpected type in convert}} 146 %0 = sparse_tensor.convert %arg0 : tensor<*xf32> to tensor<10xf32> 147 return %0 : tensor<10xf32> 148} 149 150// ----- 151 152#DCSR = #sparse_tensor.encoding<{dimLevelType = ["compressed", "compressed"]}> 153 154func.func @sparse_convert_rank_mismatch(%arg0: tensor<10x10xf64, #DCSR>) -> tensor<?xf64> { 155 // expected-error@+1 {{unexpected conversion mismatch in rank}} 156 %0 = sparse_tensor.convert %arg0 : tensor<10x10xf64, #DCSR> to tensor<?xf64> 157 return %0 : tensor<?xf64> 158} 159 160// ----- 161 162#CSR = #sparse_tensor.encoding<{dimLevelType = ["dense", "compressed"]}> 163 164func.func @sparse_convert_dim_mismatch(%arg0: tensor<10x?xf32>) -> tensor<10x10xf32, #CSR> { 165 // expected-error@+1 {{unexpected conversion mismatch in dimension 1}} 166 %0 = sparse_tensor.convert %arg0 : tensor<10x?xf32> to tensor<10x10xf32, #CSR> 167 return %0 : tensor<10x10xf32, #CSR> 168} 169 170// ----- 171 172func.func @invalid_out_dense(%arg0: tensor<10xf64>, %arg1: !llvm.ptr<i8>) { 173 // expected-error@+1 {{'sparse_tensor.out' op operand #0 must be sparse tensor of any type values, but got 'tensor<10xf64>'}} 174 sparse_tensor.out %arg0, %arg1 : tensor<10xf64>, !llvm.ptr<i8> 175 return 176} 177 178// ----- 179 180func.func @invalid_binary_num_args_mismatch_overlap(%arg0: f64, %arg1: f64) -> f64 { 181 // expected-error@+1 {{overlap region must have exactly 2 arguments}} 182 %r = sparse_tensor.binary %arg0, %arg1 : f64, f64 to f64 183 overlap={ 184 ^bb0(%x: f64): 185 sparse_tensor.yield %x : f64 186 } 187 left={} 188 right={} 189 return %r : f64 190} 191 192// ----- 193 194func.func @invalid_binary_num_args_mismatch_right(%arg0: f64, %arg1: f64) -> f64 { 195 // expected-error@+1 {{right region must have exactly 1 arguments}} 196 %r = sparse_tensor.binary %arg0, %arg1 : f64, f64 to f64 197 overlap={} 198 left={} 199 right={ 200 ^bb0(%x: f64, %y: f64): 201 sparse_tensor.yield %y : f64 202 } 203 return %r : f64 204} 205 206// ----- 207 208func.func @invalid_binary_argtype_mismatch(%arg0: f64, %arg1: f64) -> f64 { 209 // expected-error@+1 {{overlap region argument 2 type mismatch}} 210 %r = sparse_tensor.binary %arg0, %arg1 : f64, f64 to f64 211 overlap={ 212 ^bb0(%x: f64, %y: f32): 213 sparse_tensor.yield %x : f64 214 } 215 left=identity 216 right=identity 217 return %r : f64 218} 219 220// ----- 221 222func.func @invalid_binary_wrong_return_type(%arg0: f64, %arg1: f64) -> f64 { 223 // expected-error@+1 {{left region yield type mismatch}} 224 %0 = sparse_tensor.binary %arg0, %arg1 : f64, f64 to f64 225 overlap={} 226 left={ 227 ^bb0(%x: f64): 228 %1 = arith.constant 0.0 : f32 229 sparse_tensor.yield %1 : f32 230 } 231 right=identity 232 return %0 : f64 233} 234 235// ----- 236 237func.func @invalid_binary_wrong_identity_type(%arg0: i64, %arg1: f64) -> f64 { 238 // expected-error@+1 {{left=identity requires first argument to have the same type as the output}} 239 %0 = sparse_tensor.binary %arg0, %arg1 : i64, f64 to f64 240 overlap={} 241 left=identity 242 right=identity 243 return %0 : f64 244} 245 246// ----- 247 248func.func @invalid_binary_wrong_yield(%arg0: f64, %arg1: f64) -> f64 { 249 // expected-error@+1 {{left region must end with sparse_tensor.yield}} 250 %0 = sparse_tensor.binary %arg0, %arg1 : f64, f64 to f64 251 overlap={} 252 left={ 253 ^bb0(%x: f64): 254 tensor.yield %x : f64 255 } 256 right=identity 257 return %0 : f64 258} 259 260// ----- 261 262func.func @invalid_unary_argtype_mismatch(%arg0: f64) -> f64 { 263 // expected-error@+1 {{present region argument 1 type mismatch}} 264 %r = sparse_tensor.unary %arg0 : f64 to f64 265 present={ 266 ^bb0(%x: index): 267 sparse_tensor.yield %x : index 268 } 269 absent={} 270 return %r : f64 271} 272 273// ----- 274 275func.func @invalid_unary_num_args_mismatch(%arg0: f64) -> f64 { 276 // expected-error@+1 {{absent region must have exactly 0 arguments}} 277 %r = sparse_tensor.unary %arg0 : f64 to f64 278 present={} 279 absent={ 280 ^bb0(%x: f64): 281 sparse_tensor.yield %x : f64 282 } 283 return %r : f64 284} 285 286// ----- 287 288func.func @invalid_unary_wrong_return_type(%arg0: f64) -> f64 { 289 // expected-error@+1 {{present region yield type mismatch}} 290 %0 = sparse_tensor.unary %arg0 : f64 to f64 291 present={ 292 ^bb0(%x: f64): 293 %1 = arith.constant 0.0 : f32 294 sparse_tensor.yield %1 : f32 295 } 296 absent={} 297 return %0 : f64 298} 299 300// ----- 301 302func.func @invalid_unary_wrong_yield(%arg0: f64) -> f64 { 303 // expected-error@+1 {{present region must end with sparse_tensor.yield}} 304 %0 = sparse_tensor.unary %arg0 : f64 to f64 305 present={ 306 ^bb0(%x: f64): 307 tensor.yield %x : f64 308 } 309 absent={} 310 return %0 : f64 311} 312 313// ----- 314 315func.func @invalid_reduce_num_args_mismatch(%arg0: f64, %arg1: f64) -> f64 { 316 %cf1 = arith.constant 1.0 : f64 317 // expected-error@+1 {{reduce region must have exactly 2 arguments}} 318 %r = sparse_tensor.reduce %arg0, %arg1, %cf1 : f64 { 319 ^bb0(%x: f64): 320 sparse_tensor.yield %x : f64 321 } 322 return %r : f64 323} 324 325// ----- 326 327func.func @invalid_reduce_block_arg_type_mismatch(%arg0: i64, %arg1: i64) -> i64 { 328 %ci1 = arith.constant 1 : i64 329 // expected-error@+1 {{reduce region argument 1 type mismatch}} 330 %r = sparse_tensor.reduce %arg0, %arg1, %ci1 : i64 { 331 ^bb0(%x: f64, %y: f64): 332 %cst = arith.constant 2 : i64 333 sparse_tensor.yield %cst : i64 334 } 335 return %r : i64 336} 337 338// ----- 339 340func.func @invalid_reduce_return_type_mismatch(%arg0: f64, %arg1: f64) -> f64 { 341 %cf1 = arith.constant 1.0 : f64 342 // expected-error@+1 {{reduce region yield type mismatch}} 343 %r = sparse_tensor.reduce %arg0, %arg1, %cf1 : f64 { 344 ^bb0(%x: f64, %y: f64): 345 %cst = arith.constant 2 : i64 346 sparse_tensor.yield %cst : i64 347 } 348 return %r : f64 349} 350 351// ----- 352 353func.func @invalid_reduce_wrong_yield(%arg0: f64, %arg1: f64) -> f64 { 354 %cf1 = arith.constant 1.0 : f64 355 // expected-error@+1 {{reduce region must end with sparse_tensor.yield}} 356 %r = sparse_tensor.reduce %arg0, %arg1, %cf1 : f64 { 357 ^bb0(%x: f64, %y: f64): 358 %cst = arith.constant 2 : i64 359 tensor.yield %cst : i64 360 } 361 return %r : f64 362} 363