-chlo-legalize-to-stablehlo

Legalização do fluxo de operações de CHLO para operações de StableHLO e Shape

-shape-legalize-to-stablehlo

Legalizar operações relacionadas à forma para o StableHLO.

Uma passagem experimental que legaliza operações relacionadas a formas para operações StableHLO.

A união de cálculos de forma e dados por meio de um passe opcional permite que o ecossistema da StableHLO aproveite os pipelines de compilação que usam operações da StableHLO para modelar o dinamismo.

-stablehlo-aggressive-folder

Dobra as operações StableHLO

Opções

-fold-float : Allow for potentially lossy computations using float type.

-stablehlo-aggressive-simplification

Canônica as operações da StableHLO

-stablehlo-canonicalize-dynamism

Canonicização de operações estáveis de HLO dinâmicas em operações estáticas.

Substitui operações dinâmicas de StableHLO, como DynamicReshapeOp, pelas contrapartes estáticas correspondentes, como DynamicReshapeOp para ReshapeOp ou DynamicBroadcastInDim para BroadcastInDim, se todos os elementos dinâmicos dessas operações forem constantes.

  %c = stablehlo.constant dense<16> : tensor<1xi32>
  %0 = stablehlo.dynamic_broadcast_in_dim %cst, %c, dims = [] : (tensor<f32>, tensor<1xi32>) -> tensor<16xf32>

  ==>

  %0 = stablehlo.broadcast_in_dim %cst, dims = [] : (tensor<f32>) -> tensor<16xf32>

-stablehlo-compatibility-expander

Expansor de compatibilidade para operações StableHLO.

As operações StableHLO recebem atualizações ou uma nova operação é introduzida nas versões mais recentes. Esse passe de ativação amplia a compatibilidade com versões mais antigas do StableHLO decompondo operações mais recentes do StableHLO em operações equivalentes com suporte a essas versões mais antigas.

Por que esse é um cartão opcional?

Às vezes, as melhorias de operação do StableHLO são usadas para simplificar bastante o processamento de determinados padrões comuns no ecossistema do OpenXLA. Isso inclui coisas como TanOp, que tem suporte a framework e compilador, bem como dimensões de lote de coleta/dispersão, que podem ser representadas usando fatias, mas torna o particionamento muito mais difícil. Para essa categoria de novos recursos, não oferecemos downgrade automático, já que ele pode descartar informações importantes usadas em otimizações posteriores. Esse cartão pode ser usado para expandir essas operações com base em uma versão de destino para maximizar a compatibilidade à custa de uma compilação potencialmente menos otimizada.

func.func @tan_op_non_complex(%arg0: tensor<4xf64>) -> tensor<4xf64> {
  %1 = stablehlo.tan %arg0 : tensor<4xf64>
  func.return %1 : tensor<4xf64>
}

==>

func.func @tan_op_non_complex(%arg0: tensor<4xf64>) -> tensor<4xf64> {
  %0 = stablehlo.sine %arg0 : tensor<4xf64>
  %1 = stablehlo.cosine %arg0 : tensor<4xf64>
  %2 = stablehlo.divide %0, %1 : tensor<4xf64>
  return %2 : tensor<4xf64>
}

Opções

-target : The target version. Must be a version of the form #.#.#.

-stablehlo-convert-to-signless

Passe para transformar o IR em números inteiros sem sinal.

-stablehlo-legalize-composite-to-call

Substitui operações compostas por uma chamada para a decomposição delas.

Substitui operações compostas por uma chamada para a decomposição, por exemplo, a abaixo:

stablehlo.composite "my_namespace.my_op" %arg0, %arg1 {
  decomposition = @bar,
  version = 1,
  composite_attributes = {
    "my_attribute": "my_value"
  }
}

Vai se tornar:

func.call @bar(%arg0, %arg1)

Um subconjunto de compósitos pode ser excluído dessa transformação usando a flag "except", por exemplo:

stablehlo-opt --stablehlo-legalize-composite-to-call=except='foo.baz,foo.qux'

Opções

-except : Names of composites that should not be replaced with calls.

-stablehlo-legalize-deprecated-ops

Legalize operações descontinuadas para operações com suporte.

O RFC de descontinuação de Opset do StableHLO v1.0 (#2283) propõe a remoção de várias operações redundantes. Esse cartão ajuda a avaliar o impacto dessas remoções de opções em vários pipelines de compilação, legalizando-as para as contrapartes com suporte a longo prazo.

Opções

-fail-on-unused : Fail on (mostly) unused ops that are deprecated without any fallback.

-stablehlo-legalize-qdq-to-quantized-op

Fusão de padrões (de quantização, operação de ponto flutuante e quantização) na operação quantizada da StableHLO

Mesclar (operação de quantização, operação de ponto flutuante e quantização) o padrão na operação quantizada StableHLO Observação: o cartão não exclui nenhuma operação preexistente. Por exemplo, o programa a seguir

func.func @add(%arg0: tensor<16x16x!quant.uniform<ui8:f32, 34.0:16>>) -> tensor<16x16x!quant.uniform<ui8:f32, 34.0:16>> {
  %0 = stablehlo.uniform_dequantize %arg0 : (tensor<16x16x!quant.uniform<ui8:f32, 34.0:16>>) -> tensor<16x16xf32>
  %1 = stablehlo.abs %0 : tensor<16x16xf32>
  %2 = stablehlo.uniform_quantize %1 : (tensor<16x16xf32>) -> tensor<16x16x!quant.uniform<ui8:f32, 34.0:16>>
  func.return %2 : tensor<16x16x!quant.uniform<ui8:f32, 34.0:16>>
}

Vai se tornar:

func.func @add(%arg0: tensor<16x16x!quant.uniform<u8:f32, 3.400000e+01:16>>) -> tensor<16x16x!quant.uniform<u8:f32, 3.400000e+01:16>> {
  %0 = stablehlo.uniform_dequantize %arg0 : (tensor<16x16x!quant.uniform<u8:f32, 3.400000e+01:16>>) -> tensor<16x16xf32>
  %1 = stablehlo.abs %0 : tensor<16x16xf32>
  %2 = stablehlo.abs %arg0 : tensor<16x16x!quant.uniform<u8:f32, 3.400000e+01:16>>
  %3 = stablehlo.uniform_quantize %1 : (tensor<16x16xf32>) -> tensor<16x16x!quant.uniform<u8:f32, 3.400000e+01:16>>
  return %2 : tensor<16x16x!quant.uniform<u8:f32, 3.400000e+01:16>>
}

-stablehlo-legalize-quant-to-math

Conversão de operações quantizadas do StableHLO para operações matemáticas primitivas do StableHLO.

Conversão de programas StableHLO usando tipos UniformQuantized em operações matemáticas de números inteiros equivalentes semântica.

func.func @add(%arg0: tensor<!quant.uniform<i8:f32,1.0:0>>, %arg1: tensor<!quant.uniform<i8:f32,2.0:1>>) ->  tensor<!quant.uniform<i8:f32,3.0:2>> {
  %0 = "stablehlo.add"(%arg0, %arg1) : (tensor<!quant.uniform<i8:f32,1.0:0>>, tensor<!quant.uniform<i8:f32,2.0:1>>) -> tensor<!quant.uniform<i8:f32,3.0:2>>
  func.return %0 : tensor<!quant.uniform<i8:f32,3.0:2>>
}

Vai se tornar:

func.func @add(%arg0: tensor<i8>, %arg1: tensor<i8>) -> tensor<i8> {
  %0 = stablehlo.convert %arg0 : (tensor<i8>) -> tensor<f32>
  %cst = stablehlo.constant dense<0.333333343> : tensor<f32>
  %1 = chlo.broadcast_multiply %0, %cst : (tensor<f32>, tensor<f32>) -> tensor<f32>
  %cst_0 = stablehlo.constant dense<2.000000e+00> : tensor<f32>
  %2 = chlo.broadcast_add %1, %cst_0 : (tensor<f32>, tensor<f32>) -> tensor<f32>
  %3 = stablehlo.round_nearest_even %2 : tensor<f32>
  %4 = stablehlo.convert %3 : (tensor<f32>) -> tensor<i32>
  %5 = stablehlo.convert %arg1 : (tensor<i8>) -> tensor<f32>
  %cst_1 = stablehlo.constant dense<0.666666686> : tensor<f32>
  %6 = chlo.broadcast_multiply %5, %cst_1 : (tensor<f32>, tensor<f32>) -> tensor<f32>
  %cst_2 = stablehlo.constant dense<1.33333337> : tensor<f32>
  %7 = chlo.broadcast_add %6, %cst_2 : (tensor<f32>, tensor<f32>) -> tensor<f32>
  %8 = stablehlo.round_nearest_even %7 : tensor<f32>
  %9 = stablehlo.convert %8 : (tensor<f32>) -> tensor<i32>
  %c = stablehlo.constant dense<2> : tensor<i32>
  %10 = chlo.broadcast_add %4, %9 : (tensor<i32>, tensor<i32>) -> tensor<i32>
  %11 = chlo.broadcast_subtract %10, %c : (tensor<i32>, tensor<i32>) -> tensor<i32>
  %c_3 = stablehlo.constant dense<-128> : tensor<i32>
  %c_4 = stablehlo.constant dense<127> : tensor<i32>
  %12 = stablehlo.clamp %c_3, %11, %c_4 : tensor<i32>
  %13 = stablehlo.convert %12 : (tensor<i32>) -> tensor<i8>
  return %13 : tensor<i8>
}

-stablehlo-legalize-quantized-op-to-qdq

Decompõe a operação quantizada StableHLO no padrão (de-quantização, operação de ponto flutuante e quantização).

Decompor programas quantizados da StableHLO usando operações uniformes de quantização/desquantização. Por exemplo, o programa a seguir

func.func @add(%arg0: tensor<!quant.uniform<i8:f32,1.0:0>>, %arg1: tensor<!quant.uniform<i8:f32,2.0:1>>) ->  tensor<!quant.uniform<i8:f32,3.0:2>> {
  %0 = "stablehlo.add"(%arg0, %arg1) : (tensor<!quant.uniform<i8:f32,1.0:0>>, tensor<!quant.uniform<i8:f32,2.0:1>>) -> tensor<!quant.uniform<i8:f32,3.0:2>>
  func.return %0 : tensor<!quant.uniform<i8:f32,3.0:2>>
}

Vai se tornar:

func.func @add(%arg0: tensor<!quant.uniform<i8:f32, 1.000000e+00>>, %arg1: tensor<!quant.uniform<i8:f32, 2.000000e+00:1>>) -> tensor<!quant.uniform<i8:f32, 3.000000e+00:2>> {
  %0 = stablehlo.uniform_dequantize %arg0 : (tensor<!quant.uniform<i8:f32, 1.000000e+00>>) -> tensor<f32>
  %1 = stablehlo.uniform_dequantize %arg1 : (tensor<!quant.uniform<i8:f32, 2.000000e+00:1>>) -> tensor<f32>
  %2 = stablehlo.add %0, %1 : tensor<f32>
  %3 = stablehlo.uniform_quantize %2 : (tensor<f32>) -> tensor<!quant.uniform<i8:f32, 3.000000e+00:2>>
  return %3 : tensor<!quant.uniform<i8:f32, 3.000000e+00:2>>
}

-stablehlo-legalize-to-vhlo

Legalize StableHLO para VHLO.

-stablehlo-refine-arguments

Refina as formas de argumento da função principal.

Modifica os argumentos da função principal usando a assinatura do tipo de entrada. Envolve argumentos em custom_call @stablehlo.shape_refinement_operand_wrapper para manter o IR válido antes que o refinamento de forma seja executado.

func.func public @main(%arg0: tensor<?xf32>) -> tensor<?xf32> {
  ...
}

==>

func.func public @main(%arg0: tensor<16xf32>) -> tensor<?xf32> {
  %c = stablehlo.constant dense<16> : tensor<1xi64>
  %0 = stablehlo.custom_call @stablehlo.shape_refinement_operand_wrapper(%arg0, %c) {...}
    : (tensor<16xf32>, tensor<1xi64>) -> tensor<?xf32>
  ...

O refinedTypesOption pode ser usado para especificar uma lista de tipos refinados. Isso pode ser especificado no MLIR com --types='tensor<...>,tensor<...>' ou transmitido ao método de criação do cartão. A lista de tipos de refinamento precisa especificar o tipo de cada argumento para o método main que está sendo refinado.

Opções

-types : The new types to be used for the main function's arguments, specified as an MLIR TypeRange 'tensor<1x2xf32>, ...'

-stablehlo-refine-shapes

Aprimora as formas em um programa StableHLO.

Explica um programa StableHLO que refina formas nas operações.

O caso de uso principal desse cartão é especializar programas com formato dinâmico em formas estáticas. Se um programa StableHLO com formato dinâmico tiver a estrutura certa, atualizar os tipos de argumento de formas dinâmicas para estáticas e executar essa passagem vai propagar formas estáticas por todo o programa.

Essa passagem remove custom_call @shape_refinement_operand_wrapper substituindo os usos do resultado pelo operando diretamente e propaga formas estáticas em todo o programa.

  %c = stablehlo.constant dense<16> : tensor<1xi64>
  %0 = stablehlo.custom_call @stablehlo.shape_refinement_operand_wrapper(%arg0, %c) {...}
      : (tensor<16xf32>, tensor<1xi64>) -> tensor<?xf32>
  %1 = stablehlo.add %0, %0 : tensor<?xf32>

  ==>

  %1 = stablehlo.add %arg0, %arg0 : tensor<16xf32>

Os módulos válidos para refinamento de forma precisam ter as seguintes propriedades:

  • Todas as formas dinâmicas dependem apenas das formas de entrada (sem dependência de forma nos conteúdos da matriz de entrada). As operações que dependem transitivamente apenas das formas de entrada (por exemplo, conforme fornecido por stablehlo.get_dimension_size) ou constantes globais, como os valores resolvidos de números inteiros simbólicos (ou seja, tensor : A = 5), são chamadas de operações dimension. Todos os valores de dimensão podem ser resolvidos em constantes com a dobragem de constantes interprocedural.
  • As funções intermediárias podem receber vários argumentos de token (do tipo !stablehlo.token) no início da lista de argumentos, seguidos por alguns argumentos constantes globais que são escalares inteiros constantes, como os valores resolvidos de números inteiros simbólicos (ou seja, tensor : A = 5).
  • Algumas funções intermediárias podem retornar cálculos em constantes globais, ou seja, floordiv em valores de symint. Essas funções são indicadas apenas retornando valores constantes após o refinamento. Essas funções são inline.
  • Todas as chamadas para uma única função são resolvidas com as mesmas formas de argumento, e nenhuma chamada de função recursiva / co-recursiva é feita. ### -vhlo-legalize-to-stablehlo

Legalize VHLO para StableHLO.

-vhlo-to-version

Converter entre versões do VHLO.

Opções

-target : The target version. Must be a version of the form #.#.# .