• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1// Copyright 2020 The TensorFlow Authors. All Rights Reserved.
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7//     http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14
15// Revision History
16// Version 0: Initial version.
17// Version 1: Add subgraphs to schema.
18// Version 2: Rename operators to conform to NN API.
19// Version 3: Move buffer data from Model.Subgraph.Tensors to Model.Buffers.
20
21namespace tflite;
22
23// This corresponds to the version.
24file_identifier "TFL3";
25// File extension of any written files.
26file_extension "tflite";
27
28// IMPORTANT: All new members of tables, enums and unions must be added at the
29// end to ensure backwards compatibility.
30
31// The type of data stored in a tensor.
32enum TensorType : byte {
33  FLOAT32 = 0,
34  FLOAT16 = 1,
35  INT32 = 2,
36  UINT8 = 3,
37  INT64 = 4,
38  STRING = 5,
39  BOOL = 6,
40  INT16 = 7,
41  COMPLEX64 = 8,
42  INT8 = 9,
43  FLOAT64 = 10,
44}
45
46// Custom quantization parameters for experimenting with new quantization
47// techniques.
48table CustomQuantization {
49  custom:[ubyte] (force_align: 16);
50}
51
52// Represents a specific quantization technique's parameters.
53union QuantizationDetails {
54  CustomQuantization,
55}
56
57// Parameters for converting a quantized tensor back to float.
58table QuantizationParameters {
59  // These four parameters are the asymmetric linear quantization parameters.
60  // Given a quantized value q, the corresponding float value f should be:
61  //   f = scale * (q - zero_point)
62  // For other quantization types, the QuantizationDetails below is used.
63  min:[float];  // For importing back into tensorflow.
64  max:[float];  // For importing back into tensorflow.
65  scale:[float];  // For dequantizing the tensor's values.
66  zero_point:[long];
67
68  // If this is not none, the other quantization parameters (i.e. min, max,
69  // scale, zero_point fields above) are ignored and the value of the
70  // QuantizationDetails union should be used.
71  details:QuantizationDetails;
72
73  // Specifies the dimension of the Tensor's shape that the scales and
74  // zero_points correspond to. For example, a tensor t, with dims=[4, 3, 2, 1]
75  // with quantization params:
76  //   scale=[1.0, 2.0, 3.0], zero_point=[1, 2, 3], quantization_dimension=1
77  // will be quantized across the second dimension of t.
78  //   t[:, 0, :, :] will have scale[0]=1.0, zero_point[0]=1
79  //   t[:, 1, :, :] will have scale[1]=2.0, zero_point[0]=2
80  //   t[:, 2, :, :] will have scale[2]=3.0, zero_point[0]=3
81  quantized_dimension:int;
82}
83
84// Sparse tensors.
85// We use a modification of the TACO format.
86// Reference: http://tensor-compiler.org/kjolstad-oopsla17-tensor-compiler.pdf
87//
88// To encode a conceptual n-dimensional dense tensor with dims (d0, ..., dn-1),
89// potentially with a k-dimensional block (0 <= k <= n) with dims
90// (dn, ..., dn+k-1), the format needs to specify:
91//   1. In what order to traverse these dimensions. For example, to store a 2-D
92//      matrix in row major order, the traversal order would be (d0, d1),
93//      whereas to store it in column major order, the traversal order would be
94//      (d1, d0). If the 2-D matrix has a 2-D inner block, the traversal order
95//      could be (d0, d1, d2, d3).
96//   2. How each block dimension in (dn, ..., dn+k-1) maps to the original
97//      tensor dimension in (d0, ..., dn-1).
98//   3. In the traversal order defined above, the format (dense vs. sparse) and
99//      index metadata for each dimension. For a dense dimension, this is just
100//      the size of that dimension. For a sparse dimension, it's the same as
101//      the compressed index defined in the Compressed Sparse Row (CSR) format.
102//      (http://scipy-lectures.org/advanced/scipy_sparse/csr_matrix.html)
103
104// The storage type for a dimension. Currently we support:
105//   1. DENSE: each coordinate in this dimension is stored implicitly.
106//   2. SPARSE_CSR: only the coordinates with non-zero elements are stored. The
107//      compression technique is the same what CSR uses.
108// More types like a sparse dimension with a different compression technique
109// could be added to the list in the future.
110enum DimensionType : byte {
111  DENSE = 0,
112  SPARSE_CSR = 1,
113}
114
115table Int32Vector {
116  values:[int];
117}
118
119table Uint16Vector {
120  values:[ushort] (force_align: 4);
121}
122
123table Uint8Vector {
124  values:[ubyte] (force_align: 4);
125}
126
127// Variable-typed buffer to store the index metadata for a sparse dimension.
128// The widest type is Int32 instead of UInt32 because tensor's shape is a int32
129// vector. We don't want the per-dimensional index to overflow that range.
130union SparseIndexVector {
131  Int32Vector,
132  Uint16Vector,
133  Uint8Vector
134}
135
136table DimensionMetadata {
137  // Whether a dimension is dense or sparse.
138  format:DimensionType;
139  // Index metadata used for a dimension.
140  //   - If format is DimensionType.DENSE then we use the dense_size field to
141  //     store the size of that dimension. Each index in that dimension is
142  //     stored implicitly.
143  //   - If format is DimensionType.SPARSE_CSR then we use array_segments and
144  //     array_indices to encode that dimension. array_segments represents how
145  //     to segment the indices array, each segment corresponds to one element
146  //     in the previous dimension. array_indices represents the index of the
147  //     non-zero elements within this dimension (as those in the CSR matrix
148  //     format, where the first array is row pointers and the second array is
149  //     column indices).
150  dense_size:int;
151  array_segments:SparseIndexVector;
152  array_indices:SparseIndexVector;
153}
154
155// Parameters to encode a sparse TfLite tensor.
156table SparsityParameters {
157  // The traversal order of the dimensions defined in the `shape` field of the
158  // conceptual dense tensor. For a n-dimensional tensors with dims (d0, d1,
159  // ..., dn-1),
160  //   - if not block sparse, the traversal_order is just a permutation of (d0,
161  //     ..., dn-1). For example, a 2-D matrix stored in row-major order would
162  //     have traversal_order = (d0, d1).
163  //   - if block sparse with a k-dimensional block (0 <= k <= n), the
164  //     traversal_order has n + k elements. The first n elements are still a
165  //     permutation of (d0, ..., dn-1). The lask k elements are a permutation
166  //     of (dn, ..., dn+k-1), defining how to traverse a block internally. For
167  //     example, a 2-D matrix with 2-D blocks, both stored in row-major order
168  //     would have traversal_order = (d0, d1, d2, d3).
169  traversal_order:[int];
170  // For an n-dimensional tensor with a k-dimensional block (0 <= k <= n),
171  // stores how a block dimension in (dn, ..., dn+k-1) maps to the original
172  // tensor dimension in (d0, ..., dn).
173  // It's stored in the order of (dn, ..., dn+k-1).
174  // If not block-sparse, this field is NULL.
175  block_map:[int];
176  // In the traversal order defined above, the metadata needed for
177  // each dimension to locate the non-zero values in the original dense tensor.
178  // The size of the dim_metadata array = the size of the traversal_order array
179  // = n + k.
180  dim_metadata:[DimensionMetadata];
181}
182
183table Tensor {
184  // The tensor shape. The meaning of each entry is operator-specific but
185  // builtin ops use: [batch size, height, width, number of channels] (That's
186  // Tensorflow's NHWC).
187  shape:[int];
188  type:TensorType;
189  // An index that refers to the buffers table at the root of the model. Or,
190  // if there is no data buffer associated (i.e. intermediate results), then
191  // this is 0 (which refers to an always existent empty buffer).
192  //
193  // The data_buffer itself is an opaque container, with the assumption that the
194  // target device is little-endian. In addition, all builtin operators assume
195  // the memory is ordered such that if `shape` is [4, 3, 2], then index
196  // [i, j, k] maps to data_buffer[i*3*2 + j*2 + k].
197  buffer:uint;
198  name:string;  // For debugging and importing back into tensorflow.
199  quantization:QuantizationParameters;  // Optional.
200
201  is_variable:bool = false;
202
203  // Parameters to encode a sparse tensor. See the example in
204  // tensorflow/lite/testdata/sparse_tensor.json.
205  sparsity:SparsityParameters;  // Optional.
206
207  // Encodes `shape` with unknown dimensions. Unknown dimensions are
208  // represented with -1.
209  shape_signature:[int]; // Optional.
210}
211
212// A list of builtin operators. Builtin operators are slightly faster than custom
213// ones, but not by much. Moreover, while custom operators accept an opaque
214// object containing configuration parameters, builtins have a predetermined
215// set of acceptable options.
216// LINT.IfChange
217enum BuiltinOperator : byte {
218  ADD = 0,
219  AVERAGE_POOL_2D = 1,
220  CONCATENATION = 2,
221  CONV_2D = 3,
222  DEPTHWISE_CONV_2D = 4,
223  DEPTH_TO_SPACE = 5,
224  DEQUANTIZE = 6,
225  EMBEDDING_LOOKUP = 7,
226  FLOOR = 8,
227  FULLY_CONNECTED = 9,
228  HASHTABLE_LOOKUP = 10,
229  L2_NORMALIZATION = 11,
230  L2_POOL_2D = 12,
231  LOCAL_RESPONSE_NORMALIZATION = 13,
232  LOGISTIC = 14,
233  LSH_PROJECTION = 15,
234  LSTM = 16,
235  MAX_POOL_2D = 17,
236  MUL = 18,
237  RELU = 19,
238  // NOTE(aselle): RELU_N1_TO_1 used to be called RELU1, but it was renamed
239  // since different model developers use RELU1 in different ways. Never
240  // create another op called RELU1.
241  RELU_N1_TO_1 = 20,
242  RELU6 = 21,
243  RESHAPE = 22,
244  RESIZE_BILINEAR = 23,
245  RNN = 24,
246  SOFTMAX = 25,
247  SPACE_TO_DEPTH = 26,
248  SVDF = 27,
249  TANH = 28,
250  CONCAT_EMBEDDINGS = 29,
251  SKIP_GRAM = 30,
252  CALL = 31,
253  CUSTOM = 32,
254  EMBEDDING_LOOKUP_SPARSE = 33,
255  PAD = 34,
256  UNIDIRECTIONAL_SEQUENCE_RNN = 35,
257  GATHER = 36,
258  BATCH_TO_SPACE_ND = 37,
259  SPACE_TO_BATCH_ND = 38,
260  TRANSPOSE = 39,
261  MEAN = 40,
262  SUB = 41,
263  DIV = 42,
264  SQUEEZE = 43,
265  UNIDIRECTIONAL_SEQUENCE_LSTM = 44,
266  STRIDED_SLICE = 45,
267  BIDIRECTIONAL_SEQUENCE_RNN = 46,
268  EXP = 47,
269  TOPK_V2 = 48,
270  SPLIT = 49,
271  LOG_SOFTMAX = 50,
272  // DELEGATE is a special op type for the operations which are delegated to
273  // other backends.
274  // WARNING: Experimental interface, subject to change
275  DELEGATE = 51,
276  BIDIRECTIONAL_SEQUENCE_LSTM = 52,
277  CAST = 53,
278  PRELU = 54,
279  MAXIMUM = 55,
280  ARG_MAX = 56,
281  MINIMUM = 57,
282  LESS = 58,
283  NEG = 59,
284  PADV2 = 60,
285  GREATER = 61,
286  GREATER_EQUAL = 62,
287  LESS_EQUAL = 63,
288  SELECT = 64,
289  SLICE = 65,
290  SIN = 66,
291  TRANSPOSE_CONV = 67,
292  SPARSE_TO_DENSE = 68,
293  TILE = 69,
294  EXPAND_DIMS = 70,
295  EQUAL = 71,
296  NOT_EQUAL = 72,
297  LOG = 73,
298  SUM = 74,
299  SQRT = 75,
300  RSQRT = 76,
301  SHAPE = 77,
302  POW = 78,
303  ARG_MIN = 79,
304  FAKE_QUANT = 80,
305  REDUCE_PROD = 81,
306  REDUCE_MAX = 82,
307  PACK = 83,
308  LOGICAL_OR = 84,
309  ONE_HOT = 85,
310  LOGICAL_AND = 86,
311  LOGICAL_NOT = 87,
312  UNPACK = 88,
313  REDUCE_MIN = 89,
314  FLOOR_DIV = 90,
315  REDUCE_ANY = 91,
316  SQUARE = 92,
317  ZEROS_LIKE = 93,
318  FILL = 94,
319  FLOOR_MOD = 95,
320  RANGE = 96,
321  RESIZE_NEAREST_NEIGHBOR = 97,
322  LEAKY_RELU = 98,
323  SQUARED_DIFFERENCE = 99,
324  MIRROR_PAD = 100,
325  ABS = 101,
326  SPLIT_V = 102,
327  UNIQUE = 103,
328  CEIL = 104,
329  REVERSE_V2 = 105,
330  ADD_N = 106,
331  GATHER_ND = 107,
332  COS = 108,
333  WHERE = 109,
334  RANK = 110,
335  ELU = 111,
336  REVERSE_SEQUENCE = 112,
337  MATRIX_DIAG = 113,
338  QUANTIZE = 114,
339  MATRIX_SET_DIAG = 115,
340  ROUND = 116,
341  HARD_SWISH = 117,
342  IF = 118,
343  WHILE = 119,
344  NON_MAX_SUPPRESSION_V4 = 120,
345  NON_MAX_SUPPRESSION_V5 = 121,
346  SCATTER_ND = 122,
347  SELECT_V2 = 123,
348  DENSIFY = 124,
349  SEGMENT_SUM = 125,
350  BATCH_MATMUL = 126
351}
352
353// Options for the builtin operators.
354union BuiltinOptions {
355  Conv2DOptions,
356  DepthwiseConv2DOptions,
357  ConcatEmbeddingsOptions,
358  LSHProjectionOptions,
359  Pool2DOptions,
360  SVDFOptions,
361  RNNOptions,
362  FullyConnectedOptions,
363  SoftmaxOptions,
364  ConcatenationOptions,
365  AddOptions,
366  L2NormOptions,
367  LocalResponseNormalizationOptions,
368  LSTMOptions,
369  ResizeBilinearOptions,
370  CallOptions,
371  ReshapeOptions,
372  SkipGramOptions,
373  SpaceToDepthOptions,
374  EmbeddingLookupSparseOptions,
375  MulOptions,
376  PadOptions,
377  GatherOptions,
378  BatchToSpaceNDOptions,
379  SpaceToBatchNDOptions,
380  TransposeOptions,
381  ReducerOptions,
382  SubOptions,
383  DivOptions,
384  SqueezeOptions,
385  SequenceRNNOptions,
386  StridedSliceOptions,
387  ExpOptions,
388  TopKV2Options,
389  SplitOptions,
390  LogSoftmaxOptions,
391  CastOptions,
392  DequantizeOptions,
393  MaximumMinimumOptions,
394  ArgMaxOptions,
395  LessOptions,
396  NegOptions,
397  PadV2Options,
398  GreaterOptions,
399  GreaterEqualOptions,
400  LessEqualOptions,
401  SelectOptions,
402  SliceOptions,
403  TransposeConvOptions,
404  SparseToDenseOptions,
405  TileOptions,
406  ExpandDimsOptions,
407  EqualOptions,
408  NotEqualOptions,
409  ShapeOptions,
410  PowOptions,
411  ArgMinOptions,
412  FakeQuantOptions,
413  PackOptions,
414  LogicalOrOptions,
415  OneHotOptions,
416  LogicalAndOptions,
417  LogicalNotOptions,
418  UnpackOptions,
419  FloorDivOptions,
420  SquareOptions,
421  ZerosLikeOptions,
422  FillOptions,
423  BidirectionalSequenceLSTMOptions,
424  BidirectionalSequenceRNNOptions,
425  UnidirectionalSequenceLSTMOptions,
426  FloorModOptions,
427  RangeOptions,
428  ResizeNearestNeighborOptions,
429  LeakyReluOptions,
430  SquaredDifferenceOptions,
431  MirrorPadOptions,
432  AbsOptions,
433  SplitVOptions,
434  UniqueOptions,
435  ReverseV2Options,
436  AddNOptions,
437  GatherNdOptions,
438  CosOptions,
439  WhereOptions,
440  RankOptions,
441  ReverseSequenceOptions,
442  MatrixDiagOptions,
443  QuantizeOptions,
444  MatrixSetDiagOptions,
445  HardSwishOptions,
446  IfOptions,
447  WhileOptions,
448  DepthToSpaceOptions,
449  NonMaxSuppressionV4Options,
450  NonMaxSuppressionV5Options,
451  ScatterNdOptions,
452  SelectV2Options,
453  DensifyOptions,
454  SegmentSumOptions,
455  BatchMatMulOptions
456}
457
458enum Padding : byte { SAME, VALID }
459
460enum ActivationFunctionType : byte {
461  NONE = 0,
462  RELU = 1,
463  RELU_N1_TO_1 = 2,
464  RELU6 = 3,
465  TANH = 4,
466  SIGN_BIT = 5,
467}
468
469table Conv2DOptions {
470  padding:Padding;
471  stride_w:int;
472  stride_h:int;
473  fused_activation_function:ActivationFunctionType;
474  dilation_w_factor:int = 1;
475  dilation_h_factor:int = 1;
476}
477
478table Pool2DOptions {
479  padding:Padding;
480  stride_w:int;
481  stride_h:int;
482  filter_width:int;
483  filter_height:int;
484  fused_activation_function:ActivationFunctionType;
485}
486
487table DepthwiseConv2DOptions {
488  // Parameters for DepthwiseConv version 1 or above.
489  padding:Padding;
490  stride_w:int;
491  stride_h:int;
492  // `depth_multiplier` is redundant. It's used by CPU kernels in
493  // TensorFlow 2.0 or below, but ignored in versions above.
494  // See comments in lite/c/builtin_op_data.h for more details.
495  depth_multiplier:int;
496  fused_activation_function:ActivationFunctionType;
497  // Parameters for DepthwiseConv version 2 or above.
498  dilation_w_factor:int = 1;
499  dilation_h_factor:int = 1;
500}
501
502table ConcatEmbeddingsOptions {
503  num_channels:int;
504  num_columns_per_channel:[int];
505  embedding_dim_per_channel:[int]; // This could be inferred from parameters.
506}
507
508enum LSHProjectionType: byte {
509  UNKNOWN = 0,
510  SPARSE = 1,
511  DENSE = 2,
512}
513
514table LSHProjectionOptions {
515  type: LSHProjectionType;
516}
517
518table SVDFOptions {
519  rank:int;
520  fused_activation_function:ActivationFunctionType;
521  // For weights-only quantization, use asymmetric quantization for non
522  // constant inputs at evaluation time.
523  asymmetric_quantize_inputs:bool;
524}
525
526// An implementation of TensorFlow RNNCell.
527table RNNOptions {
528  fused_activation_function:ActivationFunctionType;
529  asymmetric_quantize_inputs:bool;
530}
531
532// An implementation of TensorFlow dynamic_rnn with RNNCell.
533table SequenceRNNOptions {
534  time_major:bool;
535  fused_activation_function:ActivationFunctionType;
536  asymmetric_quantize_inputs:bool;
537}
538
539// An implementation of TensorFlow bidrectional_dynamic_rnn with RNNCell.
540table BidirectionalSequenceRNNOptions {
541  time_major:bool;
542  fused_activation_function:ActivationFunctionType;
543  merge_outputs: bool;
544  asymmetric_quantize_inputs:bool;
545}
546
547enum FullyConnectedOptionsWeightsFormat: byte {
548  DEFAULT = 0,
549  SHUFFLED4x16INT8 = 1,
550}
551
552// An implementation of TensorFlow fully_connected (a.k.a Dense) layer.
553table FullyConnectedOptions {
554  // Parameters for FullyConnected version 1 or above.
555  fused_activation_function:ActivationFunctionType;
556
557  // Parameters for FullyConnected version 2 or above.
558  weights_format:FullyConnectedOptionsWeightsFormat = DEFAULT;
559
560  // Parameters for FullyConnected version 5 or above.
561  // If set to true, then the number of dimension is preserved. Furthermore,
562  // all but the last dimension of the input and output shapes will be equal.
563  keep_num_dims: bool;
564
565  // Parameters for FullyConnected version 7 or above.
566  // If set to true, then weights-only op will use asymmetric quantization for
567  // inputs.
568  asymmetric_quantize_inputs: bool;
569}
570
571table SoftmaxOptions {
572  beta: float;
573}
574
575// An implementation of TensorFlow concat.
576table ConcatenationOptions {
577  axis:int;
578  fused_activation_function:ActivationFunctionType;
579}
580
581table AddOptions {
582  fused_activation_function:ActivationFunctionType;
583}
584
585table MulOptions {
586  fused_activation_function:ActivationFunctionType;
587}
588
589table L2NormOptions {
590  fused_activation_function:ActivationFunctionType;
591}
592
593table LocalResponseNormalizationOptions {
594  radius:int;
595  bias:float;
596  alpha:float;
597  beta:float;
598}
599
600enum LSTMKernelType : byte {
601  // Full LSTM kernel which supports peephole and projection.
602  FULL = 0,
603  // Basic LSTM kernels. Equivalent to TensorFlow BasicLSTMCell.
604  BASIC = 1,
605}
606
607// An implementation of TensorFlow LSTMCell and CoupledInputForgetGateLSTMCell
608table LSTMOptions {
609  // Parameters for LSTM version 1 or above.
610  fused_activation_function:ActivationFunctionType;
611  cell_clip: float; // Optional, 0.0 means no clipping
612  proj_clip: float; // Optional, 0.0 means no clipping
613
614  // Parameters for LSTM version 2 or above.
615  // Basic kernel is only supported in version 2 or above.
616  kernel_type: LSTMKernelType = FULL;
617
618  // Parameters for LSTM version 4 or above.
619  asymmetric_quantize_inputs: bool;
620}
621
622// An implementation of TensorFlow dynamic_rnn with LSTMCell.
623table UnidirectionalSequenceLSTMOptions {
624  fused_activation_function:ActivationFunctionType;
625  cell_clip: float; // Optional, 0.0 means no clipping
626  proj_clip: float; // Optional, 0.0 means no clipping
627
628  // If true then first dimension is sequence, otherwise batch.
629  time_major:bool;
630
631  // Parameter for Unidirectional Sequence LSTM version 4.
632  asymmetric_quantize_inputs:bool;
633}
634
635table BidirectionalSequenceLSTMOptions {
636  // Parameters supported by version 1:
637  fused_activation_function:ActivationFunctionType;
638  cell_clip: float; // Optional, 0.0 means no clipping
639  proj_clip: float; // Optional, 0.0 means no clipping
640
641  // If true, store the outputs of both directions into the first output.
642  merge_outputs: bool;
643
644  // Parameters supported by version 2:
645  // If true then first dimension is sequence, otherwise batch.
646  // Version 1 implementations assumed time_major to be true, so this default
647  // value should never change.
648  time_major: bool = true;
649
650  // Parameters for version 3 or above.
651  asymmetric_quantize_inputs:bool;
652}
653
654table ResizeBilinearOptions {
655  new_height: int (deprecated);
656  new_width: int (deprecated);
657  align_corners: bool;
658  half_pixel_centers: bool;
659}
660
661table ResizeNearestNeighborOptions {
662  align_corners: bool;
663}
664
665// A call operation options
666table CallOptions {
667  // The subgraph index that needs to be called.
668  subgraph:uint;
669}
670
671table PadOptions {
672}
673
674table PadV2Options {
675}
676
677table ReshapeOptions {
678  new_shape:[int];
679}
680
681table SpaceToBatchNDOptions {
682}
683
684table BatchToSpaceNDOptions {
685}
686
687table SkipGramOptions {
688  ngram_size: int;
689  max_skip_size: int;
690  include_all_ngrams: bool;
691}
692
693table SpaceToDepthOptions {
694  block_size: int;
695}
696
697table DepthToSpaceOptions {
698  block_size: int;
699}
700
701table SubOptions {
702  fused_activation_function:ActivationFunctionType;
703}
704
705table DivOptions {
706  fused_activation_function:ActivationFunctionType;
707}
708
709table TopKV2Options {
710}
711
712enum CombinerType : byte {
713  SUM = 0,
714  MEAN = 1,
715  SQRTN = 2,
716}
717
718table EmbeddingLookupSparseOptions {
719  combiner:CombinerType;
720}
721
722table GatherOptions {
723  axis: int;
724}
725
726table TransposeOptions {
727}
728
729table ExpOptions {
730}
731
732table CosOptions {
733}
734
735table ReducerOptions {
736  keep_dims: bool;
737}
738
739table SqueezeOptions {
740  squeeze_dims:[int];
741}
742
743table SplitOptions {
744  num_splits: int;
745}
746
747table SplitVOptions {
748  num_splits: int;
749}
750
751table StridedSliceOptions {
752  begin_mask: int;
753  end_mask: int;
754  ellipsis_mask: int;
755  new_axis_mask: int;
756  shrink_axis_mask: int;
757}
758
759table LogSoftmaxOptions {
760}
761
762table CastOptions {
763  in_data_type: TensorType;
764  out_data_type: TensorType;
765}
766
767table DequantizeOptions {
768}
769
770table MaximumMinimumOptions {
771}
772
773table TileOptions {
774}
775
776table ArgMaxOptions {
777  output_type : TensorType;
778}
779
780table ArgMinOptions {
781  output_type : TensorType;
782}
783
784table GreaterOptions {
785}
786
787table GreaterEqualOptions {
788}
789
790table LessOptions {
791}
792
793table LessEqualOptions {
794}
795
796table NegOptions {
797}
798
799table SelectOptions {
800}
801
802table SliceOptions {
803}
804
805table TransposeConvOptions {
806  padding:Padding;
807  stride_w:int;
808  stride_h:int;
809}
810
811table ExpandDimsOptions {
812}
813
814table SparseToDenseOptions {
815  validate_indices:bool;
816}
817
818table EqualOptions {
819}
820
821table NotEqualOptions {
822}
823
824table ShapeOptions {
825  // Optional output type of the operation (int32 or int64). Defaults to int32.
826  out_type : TensorType;
827}
828
829table RankOptions {
830}
831
832table PowOptions {
833}
834
835table FakeQuantOptions {
836  // Parameters supported by version 1:
837  min:float;
838  max:float;
839  num_bits:int;
840
841  // Parameters supported by version 2:
842  narrow_range:bool;
843}
844
845table PackOptions {
846  values_count:int;
847  axis:int;
848}
849
850table LogicalOrOptions {
851}
852
853table OneHotOptions {
854  axis:int;
855}
856
857table AbsOptions {
858}
859
860
861table HardSwishOptions {
862}
863
864table LogicalAndOptions {
865}
866
867table LogicalNotOptions {
868}
869
870table UnpackOptions {
871  num:int;
872  axis:int;
873}
874
875table FloorDivOptions {
876}
877
878table SquareOptions {
879}
880
881table ZerosLikeOptions {
882}
883
884table FillOptions {
885}
886
887table FloorModOptions {
888}
889
890table RangeOptions {
891}
892
893table LeakyReluOptions {
894  alpha:float;
895}
896
897table SquaredDifferenceOptions {
898}
899
900enum MirrorPadMode : byte {
901  // Doesn't include borders.
902  REFLECT = 0,
903  // Includes borders.
904  SYMMETRIC = 1,
905}
906
907table MirrorPadOptions {
908  mode:MirrorPadMode;
909}
910
911table UniqueOptions {
912  idx_out_type:TensorType = INT32;
913}
914
915table ReverseV2Options {
916}
917
918table AddNOptions {
919}
920
921table GatherNdOptions {
922}
923
924table WhereOptions {
925}
926
927table ReverseSequenceOptions {
928  seq_dim:int;
929  batch_dim:int = 0;
930}
931
932table MatrixDiagOptions {
933}
934
935table QuantizeOptions {
936}
937
938table MatrixSetDiagOptions {
939}
940
941table IfOptions {
942  then_subgraph_index:int;
943  else_subgraph_index:int;
944}
945
946table WhileOptions {
947  cond_subgraph_index:int;
948  body_subgraph_index:int;
949}
950
951table NonMaxSuppressionV4Options {
952}
953
954table NonMaxSuppressionV5Options {
955}
956
957table ScatterNdOptions {
958}
959
960table SelectV2Options {
961}
962
963table DensifyOptions {
964}
965
966table SegmentSumOptions {
967}
968
969table BatchMatMulOptions {
970  adjoint_lhs:bool;
971  adjoint_rhs:bool;
972}
973
974// An OperatorCode can be an enum value (BuiltinOperator) if the operator is a
975// builtin, or a string if the operator is custom.
976table OperatorCode {
977  builtin_code:BuiltinOperator;
978  custom_code:string;
979
980  // The version of the operator. The version need to be bumped whenever new
981  // parameters are introduced into an op.
982  version:int = 1;
983}
984
985enum CustomOptionsFormat : byte {
986  FLEXBUFFERS = 0,
987}
988
989// An operator takes tensors as inputs and outputs. The type of operation being
990// performed is determined by an index into the list of valid OperatorCodes,
991// while the specifics of each operations is configured using builtin_options
992// or custom_options.
993table Operator {
994  // Index into the operator_codes array. Using an integer here avoids
995  // complicate map lookups.
996  opcode_index:uint;
997
998  // Optional input are indicated by -1.
999  inputs:[int];
1000  outputs:[int];
1001
1002  builtin_options:BuiltinOptions;
1003  custom_options:[ubyte];
1004  custom_options_format:CustomOptionsFormat;
1005
1006  // A list of booleans indicating the input tensors which are being mutated by
1007  // this operator.(e.g. used by RNN and LSTM).
1008  // For example, if the "inputs" array refers to 5 tensors and the second and
1009  // fifth are mutable variables, then this list will contain
1010  // [false, true, false, false, true].
1011  //
1012  // If the list is empty, no variable is mutated in this operator.
1013  // The list either has the same length as `inputs`, or is empty.
1014  mutating_variable_inputs:[bool];
1015
1016  // A list of indices to the subgraph's "tensors" that are internal to an Op.
1017  // Internal tensors are those that do not flow in or out of the operation,
1018  // but instead are part of internal computation. As such, the operation's
1019  // implementation may manage its memory more efficiently. They are needed
1020  // however (i.e. not just an implementation detail) since they are part of the
1021  // computation, which may require relevant metadata such as quantization
1022  // parameters.
1023  intermediates:[int];
1024}
1025
1026// The root type, defining a subgraph, which typically represents an entire
1027// model.
1028table SubGraph {
1029  // A list of all tensors used in this subgraph.
1030  tensors:[Tensor];
1031
1032  // Indices of the tensors that are inputs into this subgraph. Note this is
1033  // the list of non-static tensors that feed into the subgraph for inference.
1034  inputs:[int];
1035
1036  // Indices of the tensors that are outputs out of this subgraph. Note this is
1037  // the list of output tensors that are considered the product of the
1038  // subgraph's inference.
1039  outputs:[int];
1040
1041  // All operators, in execution order.
1042  operators:[Operator];
1043
1044  // Name of this subgraph (used for debugging).
1045  name:string;
1046}
1047
1048// Table of raw data buffers (used for constant tensors). Referenced by tensors
1049// by index. The generous alignment accommodates mmap-friendly data structures.
1050table Buffer {
1051  data:[ubyte] (force_align: 16);
1052}
1053
1054table Metadata {
1055  // A human readable string to uniquely identify a Metadata.
1056  name:string;
1057  // An index to the buffers table.
1058  buffer:uint;
1059}
1060
1061table Model {
1062  // Version of the schema.
1063  version:uint;
1064
1065  // A list of all operator codes used in this model. This is
1066  // kept in order because operators carry an index into this
1067  // vector.
1068  operator_codes:[OperatorCode];
1069
1070  // All the subgraphs of the model. The 0th is assumed to be the main
1071  // model.
1072  subgraphs:[SubGraph];
1073
1074  // A description of the model.
1075  description:string;
1076
1077  // Buffers of the model.
1078  // Note the 0th entry of this array must be an empty buffer (sentinel).
1079  // This is a convention so that tensors without a buffer can provide 0 as
1080  // their buffer.
1081  buffers:[Buffer];
1082
1083  // Metadata about the model. Indirects into the existings buffers list.
1084  // Deprecated, prefer to use metadata field.
1085  metadata_buffer:[int];
1086
1087  // Metadata about the model.
1088  metadata:[Metadata];
1089}
1090
1091root_type Model;
1092