Export min_runtime_version in MLIR converter
This change fixes the issue for missing min_runtime_version in flatbuffers exported by MLIR converter. Specifically: *Export `min_runtime_version` in metadata of flatbuffer (fixed-length byte array). *Update all related mlir tests to have metadata. PiperOrigin-RevId: 299894972 Change-Id: Ic79f3ab05b593882362f5baf62493861961acbe3
This commit is contained in:
parent
356c9a830c
commit
30f3741ddf
@ -580,7 +580,7 @@ cc_library(
|
|||||||
"//tensorflow/lite/delegates/flex:whitelisted_flex_ops_lib",
|
"//tensorflow/lite/delegates/flex:whitelisted_flex_ops_lib",
|
||||||
"//tensorflow/lite/kernels/internal:kernel_utils",
|
"//tensorflow/lite/kernels/internal:kernel_utils",
|
||||||
"//tensorflow/lite/schema:schema_fbs",
|
"//tensorflow/lite/schema:schema_fbs",
|
||||||
"//tensorflow/lite/tools/versioning:op_version",
|
"//tensorflow/lite/tools/versioning",
|
||||||
"@com_google_absl//absl/base",
|
"@com_google_absl//absl/base",
|
||||||
"@com_google_absl//absl/base:core_headers",
|
"@com_google_absl//absl/base:core_headers",
|
||||||
"@com_google_absl//absl/container:flat_hash_map",
|
"@com_google_absl//absl/container:flat_hash_map",
|
||||||
|
@ -76,6 +76,7 @@ limitations under the License.
|
|||||||
#include "tensorflow/lite/schema/schema_generated.h"
|
#include "tensorflow/lite/schema/schema_generated.h"
|
||||||
#include "tensorflow/lite/string_util.h"
|
#include "tensorflow/lite/string_util.h"
|
||||||
#include "tensorflow/lite/tools/versioning/op_version.h"
|
#include "tensorflow/lite/tools/versioning/op_version.h"
|
||||||
|
#include "tensorflow/lite/tools/versioning/runtime_version.h"
|
||||||
#include "tensorflow/lite/version.h"
|
#include "tensorflow/lite/version.h"
|
||||||
|
|
||||||
using llvm::dyn_cast;
|
using llvm::dyn_cast;
|
||||||
@ -1230,21 +1231,27 @@ BufferOffset<tflite::Metadata> Translator::BuildMetadata(StringRef name,
|
|||||||
Optional<VectorBufferOffset<BufferOffset<tflite::Metadata>>>
|
Optional<VectorBufferOffset<BufferOffset<tflite::Metadata>>>
|
||||||
Translator::CreateMetadataVector() {
|
Translator::CreateMetadataVector() {
|
||||||
auto dict_attr = module_.getAttrOfType<mlir::DictionaryAttr>("tfl.metadata");
|
auto dict_attr = module_.getAttrOfType<mlir::DictionaryAttr>("tfl.metadata");
|
||||||
if (!dict_attr) return VectorBufferOffset<BufferOffset<tflite::Metadata>>();
|
|
||||||
|
|
||||||
std::vector<BufferOffset<tflite::Metadata>> metadata;
|
std::vector<BufferOffset<tflite::Metadata>> metadata;
|
||||||
for (const auto& named_attr : dict_attr) {
|
if (dict_attr) {
|
||||||
StringRef name = named_attr.first;
|
for (const auto& named_attr : dict_attr) {
|
||||||
mlir::Attribute attr = named_attr.second;
|
StringRef name = named_attr.first;
|
||||||
if (auto content = attr.dyn_cast<StringAttr>()) {
|
mlir::Attribute attr = named_attr.second;
|
||||||
metadata.push_back(BuildMetadata(name, content.getValue()));
|
if (auto content = attr.dyn_cast<StringAttr>()) {
|
||||||
} else {
|
metadata.push_back(BuildMetadata(name, content.getValue()));
|
||||||
module_.emitError(
|
} else {
|
||||||
"all values in tfl.metadata's dictionary key-value pairs should be "
|
module_.emitError(
|
||||||
"string attributes");
|
"all values in tfl.metadata's dictionary key-value pairs should be "
|
||||||
return llvm::None;
|
"string attributes");
|
||||||
|
return llvm::None;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// Runtime version string is generated after we update the op
|
||||||
|
// versions. Here we put a 16-byte dummy string as a placeholder. We choose
|
||||||
|
// 16-byte because it's the alignment of buffers in flatbuffer, so it won't
|
||||||
|
// cause any waste of space if the actual string is shorter than 16 bytes.
|
||||||
|
metadata.push_back(
|
||||||
|
BuildMetadata("min_runtime_version", std::string(16, '\0')));
|
||||||
return builder_.CreateVector(metadata);
|
return builder_.CreateVector(metadata);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1359,6 +1366,7 @@ Optional<std::string> Translator::TranslateInternal() {
|
|||||||
builder_.CreateVector(buffers_), metadata_buffer, *metadata);
|
builder_.CreateVector(buffers_), metadata_buffer, *metadata);
|
||||||
tflite::FinishModelBuffer(builder_, model);
|
tflite::FinishModelBuffer(builder_, model);
|
||||||
tflite::UpdateOpVersion(builder_.GetBufferPointer());
|
tflite::UpdateOpVersion(builder_.GetBufferPointer());
|
||||||
|
tflite::UpdateMinimumRuntimeVersionForModel(builder_.GetBufferPointer());
|
||||||
|
|
||||||
// Return serialized string for the built FlatBuffer.
|
// Return serialized string for the built FlatBuffer.
|
||||||
return std::string(reinterpret_cast<const char*>(builder_.GetBufferPointer()),
|
return std::string(reinterpret_cast<const char*>(builder_.GetBufferPointer()),
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
# RUN: tf_tfl_translate -tf-input-arrays=input0,input1 -tf-input-shapes=4:4 -tf-input-data-types=DT_INT32,DT_INT32 -tf-output-arrays=Add %s -o - | flatbuffer_to_string - | FileCheck %s
|
# RUN: tf_tfl_translate -tf-input-arrays=input0,input1 -tf-input-shapes=4:4 -tf-input-data-types=DT_INT32,DT_INT32 -tf-output-arrays=Add %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
# Add two tensor<4xi32> inputs and return the result
|
# Add two tensor<4xi32> inputs and return the result
|
||||||
|
|
||||||
@ -90,5 +90,11 @@ versions {
|
|||||||
# CHECK-EMPTY:
|
# CHECK-EMPTY:
|
||||||
# CHECK-NEXT: }, {
|
# CHECK-NEXT: }, {
|
||||||
# CHECK-EMPTY:
|
# CHECK-EMPTY:
|
||||||
|
# CHECK-NEXT: }, {
|
||||||
|
# CHECK-NEXT: data: [ 49, 46, 53, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
# CHECK-NEXT: } ],
|
||||||
|
# CHECK-NEXT: metadata: [ {
|
||||||
|
# CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
# CHECK-NEXT: buffer: 4
|
||||||
# CHECK-NEXT: } ]
|
# CHECK-NEXT: } ]
|
||||||
# CHECK-NEXT: }
|
# CHECK-NEXT: }
|
||||||
|
@ -108,6 +108,12 @@ func @main(tensor<1x384xf32>, tensor<1x96xf32>, tensor<384x480xf32>, tensor<384x
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 48, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 10
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-custom-ops -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-custom-ops -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_translate --tflite-flatbuffer-to-mlir -o - | FileCheck --check-prefix=MLIR %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_translate --tflite-flatbuffer-to-mlir -o - | FileCheck --check-prefix=MLIR %s
|
||||||
|
|
||||||
|
|
||||||
@ -61,6 +61,12 @@ func @main(%arg0: tensor<32x4x4x128xf32>, %arg1: tensor<1x32x42x128xf32>, %arg2:
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 5
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-custom-ops -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-custom-ops -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4xf32>) -> tensor<4xf32> {
|
func @main(tensor<4xf32>) -> tensor<4xf32> {
|
||||||
^bb0(%arg0: tensor<4xf32>):
|
^bb0(%arg0: tensor<4xf32>):
|
||||||
@ -90,6 +90,12 @@ func @main(tensor<4xf32>) -> tensor<4xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 55, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 6
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -82,6 +82,12 @@ func @main(tensor<1x224x224x3xf32>) -> tensor<1x112x112x32xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 51, 46, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 6
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -84,6 +84,12 @@ func @main(tensor<1x224x224x3xf32>) -> tensor<1x112x112x32xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 51, 46, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 6
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4xf32>) -> tensor<4xf32> {
|
func @main(tensor<4xf32>) -> tensor<4xf32> {
|
||||||
^bb0(%arg0: tensor<4xf32>):
|
^bb0(%arg0: tensor<4xf32>):
|
||||||
@ -88,6 +88,12 @@ func @main(tensor<4xf32>) -> tensor<4xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 55, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 6
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_translate -tflite-flatbuffer-to-mlir - -o - | FileCheck --check-prefix=IMPORT %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_translate -tflite-flatbuffer-to-mlir - -o - | FileCheck --check-prefix=IMPORT %s
|
||||||
|
|
||||||
func @main(tensor<4xf32>) -> tensor<4xf32> {
|
func @main(tensor<4xf32>) -> tensor<4xf32> {
|
||||||
@ -46,6 +46,12 @@ func @main(tensor<4xf32>) -> tensor<4xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 53, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 3
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-select-tf-ops=true -emit-builtin-tflite-ops=false -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-select-tf-ops=true -emit-builtin-tflite-ops=false -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(%arg0: tensor<3x2xf32>) -> tensor<3x2xf32> {
|
func @main(%arg0: tensor<3x2xf32>) -> tensor<3x2xf32> {
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
@ -39,6 +39,12 @@ func @main(%arg0: tensor<3x2xf32>) -> tensor<3x2xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 3
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-select-tf-ops -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-select-tf-ops -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4xf32>) -> tensor<4xf32> {
|
func @main(tensor<4xf32>) -> tensor<4xf32> {
|
||||||
^bb0(%arg0: tensor<4xf32>):
|
^bb0(%arg0: tensor<4xf32>):
|
||||||
@ -89,6 +89,12 @@ func @main(tensor<4xf32>) -> tensor<4xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 55, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 6
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -61,6 +61,12 @@ func @main(tensor<40x37xf32>, tensor<40x37xf32>) -> tensor<40x40xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 53, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 5
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -61,6 +61,12 @@ func @main(tensor<40x37xf32>, tensor<40x37xf32>) -> tensor<40x40xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 48, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 5
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -156,6 +156,12 @@
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 52, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 11
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4xi1>) -> tensor<4xi1> {
|
func @main(tensor<4xi1>) -> tensor<4xi1> {
|
||||||
^bb0(%arg0: tensor<4xi1>):
|
^bb0(%arg0: tensor<4xi1>):
|
||||||
@ -78,6 +78,12 @@ func @main(tensor<4xi1>) -> tensor<4xi1> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 49, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 6
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
@ -249,6 +249,12 @@ func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, t
|
|||||||
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 55, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 26
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
@ -128,6 +128,12 @@ func @main(tensor<4xf32>) -> tensor<4xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 51, 46, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 8
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-custom-ops -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-custom-ops -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_translate --tflite-flatbuffer-to-mlir -o - | FileCheck --check-prefix=MLIR %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_translate --tflite-flatbuffer-to-mlir -o - | FileCheck --check-prefix=MLIR %s
|
||||||
|
|
||||||
func @main(%arg0: tensor<1x64x64x32xf32>) -> (tensor<1x32x32x32xf32>, tensor<1x32x32x32xf32>) {
|
func @main(%arg0: tensor<1x64x64x32xf32>) -> (tensor<1x32x32x32xf32>, tensor<1x32x32x32xf32>) {
|
||||||
@ -50,6 +50,12 @@ func @main(%arg0: tensor<1x64x64x32xf32>) -> (tensor<1x32x32x32xf32>, tensor<1x3
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 4
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-custom-ops -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -emit-custom-ops -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_translate --tflite-flatbuffer-to-mlir -o - | FileCheck --check-prefix=MLIR %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_translate --tflite-flatbuffer-to-mlir -o - | FileCheck --check-prefix=MLIR %s
|
||||||
|
|
||||||
func @main(%arg0: tensor<1x8x8x128xf32>, %arg1: tensor<1x8x8x128xf32>) -> tensor<1x8x8x128xf32> {
|
func @main(%arg0: tensor<1x8x8x128xf32>, %arg1: tensor<1x8x8x128xf32>) -> tensor<1x8x8x128xf32> {
|
||||||
@ -50,6 +50,12 @@ func @main(%arg0: tensor<1x8x8x128xf32>, %arg1: tensor<1x8x8x128xf32>) -> tensor
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 4
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -20,6 +20,8 @@ module attributes {
|
|||||||
// CHECK-NEXT: data: [ 118, 97, 108, 117, 101, 49 ]
|
// CHECK-NEXT: data: [ 118, 97, 108, 117, 101, 49 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-NEXT: data: [ 118, 97, 108, 117, 101, 50 ]
|
// CHECK-NEXT: data: [ 118, 97, 108, 117, 101, 50 ]
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 54, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
// CHECK-NEXT: } ],
|
// CHECK-NEXT: } ],
|
||||||
// CHECK-NEXT: metadata: [ {
|
// CHECK-NEXT: metadata: [ {
|
||||||
// CHECK-NEXT: name: "key1",
|
// CHECK-NEXT: name: "key1",
|
||||||
@ -27,4 +29,8 @@ module attributes {
|
|||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-NEXT: name: "key2",
|
// CHECK-NEXT: name: "key2",
|
||||||
// CHECK-NEXT: buffer: 5
|
// CHECK-NEXT: buffer: 5
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 6
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
|
// CHECK-NEXT: }
|
||||||
|
@ -58,6 +58,12 @@ func @main(tensor<3x!quant.uniform<i8:f32, 0.1>>) -> tensor<3x!quant.uniform<i8:
|
|||||||
// CHECK-NEXT: data: [ 2, 2, 2 ]
|
// CHECK-NEXT: data: [ 2, 2, 2 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 52, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 4
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -58,6 +58,12 @@ func @main(tensor<3x!quant.uniform<i8:f32, 1.0>>) -> tensor<3x!quant.uniform<i8:
|
|||||||
// CHECK-NEXT: data: [ 2, 2, 2 ]
|
// CHECK-NEXT: data: [ 2, 2, 2 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 53, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 4
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<1x6x6x16xf32>) -> tensor<1x1x1x16xf32> {
|
func @main(tensor<1x6x6x16xf32>) -> tensor<1x1x1x16xf32> {
|
||||||
^bb0(%arg0: tensor<1x6x6x16xf32>):
|
^bb0(%arg0: tensor<1x6x6x16xf32>):
|
||||||
@ -47,6 +47,12 @@ func @main(tensor<1x6x6x16xf32>) -> tensor<1x1x1x16xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 53, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 3
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
// CHECK-NEXT: version: 3,
|
// CHECK-NEXT: version: 3,
|
||||||
@ -40,6 +40,12 @@
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 3
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(%arg0: tensor<1x224x224x3xf32>) -> tensor<1x1001xf32> {
|
func @main(%arg0: tensor<1x224x224x3xf32>) -> tensor<1x1001xf32> {
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
@ -153,6 +153,12 @@ func @main(%arg0: tensor<1x224x224x3xf32>) -> tensor<1x1001xf32> {
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 51, 46, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 10
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT:}
|
// CHECK-NEXT:}
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<3x2xi32>) -> tensor<6xi32> {
|
func @main(tensor<3x2xi32>) -> tensor<6xi32> {
|
||||||
^bb0(%arg0: tensor<3x2xi32>):
|
^bb0(%arg0: tensor<3x2xi32>):
|
||||||
@ -51,6 +51,12 @@ func @main(tensor<3x2xi32>) -> tensor<6xi32> {
|
|||||||
// CHECK-NEXT: data: [ 6, 0, 0, 0 ]
|
// CHECK-NEXT: data: [ 6, 0, 0, 0 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 53, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 4
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -97,6 +97,12 @@ func @main(tensor<3x2xi32>) -> tensor<3x2xi32>
|
|||||||
// CHECK-NEXT: data: [ 10, 0, 0, 0 ]
|
// CHECK-NEXT: data: [ 10, 0, 0, 0 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 54, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 6
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
@ -79,6 +79,12 @@ func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -
|
|||||||
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 53, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 7
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4 x f32>, tensor<4 x i8>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
func @main(tensor<4 x f32>, tensor<4 x i8>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
@ -80,6 +80,12 @@ func @main(tensor<4 x f32>, tensor<4 x i8>, tensor<4 x f32>, tensor<4 x f32>) ->
|
|||||||
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 52, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 7
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
@ -189,6 +189,12 @@
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 52, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 14
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
@ -249,6 +249,12 @@ func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, t
|
|||||||
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 51, 46, 49, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 26
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -> tensor<4 x f32> {
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
@ -79,6 +79,12 @@ func @main(tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>, tensor<4 x f32>) -
|
|||||||
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
// CHECK-NEXT: data: [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 52, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 7
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck %s
|
// RUN: flatbuffer_translate -mlir-to-tflite-flatbuffer %s -o - | flatbuffer_to_string - | FileCheck --dump-input-on-failure %s
|
||||||
|
|
||||||
// CHECK: {
|
// CHECK: {
|
||||||
// CHECK-NEXT: version: 3,
|
// CHECK-NEXT: version: 3,
|
||||||
@ -189,6 +189,12 @@
|
|||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
// CHECK-NEXT: }, {
|
// CHECK-NEXT: }, {
|
||||||
// CHECK-EMPTY:
|
// CHECK-EMPTY:
|
||||||
|
// CHECK-NEXT: }, {
|
||||||
|
// CHECK-NEXT: data: [ 49, 46, 49, 52, 46, 48, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ]
|
||||||
|
// CHECK-NEXT: } ],
|
||||||
|
// CHECK-NEXT: metadata: [ {
|
||||||
|
// CHECK-NEXT: name: "min_runtime_version",
|
||||||
|
// CHECK-NEXT: buffer: 14
|
||||||
// CHECK-NEXT: } ]
|
// CHECK-NEXT: } ]
|
||||||
// CHECK-NEXT: }
|
// CHECK-NEXT: }
|
||||||
|
|
||||||
|
@ -163,7 +163,7 @@ execute the op. In this example, it means:
|
|||||||
* Populate version=2 otherwise.
|
* Populate version=2 otherwise.
|
||||||
|
|
||||||
To do this, you need to override `GetVersion` function for the operator class in
|
To do this, you need to override `GetVersion` function for the operator class in
|
||||||
`lite/toco/tflite/operator.cc`.
|
`lite/tools/versioning/op_version.cc`.
|
||||||
|
|
||||||
For ops with only one version, the `GetVersion` function is defined as:
|
For ops with only one version, the `GetVersion` function is defined as:
|
||||||
|
|
||||||
@ -191,7 +191,8 @@ The last step is to add the new version info into the operator version map. This
|
|||||||
step is required because we need generate the model's minimum required runtime
|
step is required because we need generate the model's minimum required runtime
|
||||||
version based on this version map.
|
version based on this version map.
|
||||||
|
|
||||||
To do this, you need to add a new map entry in `lite/toco/tflite/op_version.cc`.
|
To do this, you need to add a new map entry in
|
||||||
|
`lite/tools/versioning/op_version.cc`.
|
||||||
|
|
||||||
In this example, it means you need to add the following into `op_version_map`:
|
In this example, it means you need to add the following into `op_version_map`:
|
||||||
```
|
```
|
||||||
|
@ -182,7 +182,7 @@ cc_library(
|
|||||||
"//tensorflow/lite/testing:util",
|
"//tensorflow/lite/testing:util",
|
||||||
"//tensorflow/lite/tools/optimize:quantization_utils",
|
"//tensorflow/lite/tools/optimize:quantization_utils",
|
||||||
"//tensorflow/lite/tools/optimize/sparsity:format_converter",
|
"//tensorflow/lite/tools/optimize/sparsity:format_converter",
|
||||||
"//tensorflow/lite/tools/versioning:op_version",
|
"//tensorflow/lite/tools/versioning",
|
||||||
"@com_google_googletest//:gtest",
|
"@com_google_googletest//:gtest",
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
@ -225,8 +225,20 @@ string FlatBufferModel::GetMinimumRuntime() const {
|
|||||||
auto buf = metadata->buffer();
|
auto buf = metadata->buffer();
|
||||||
auto* buffer = (*model_->buffers())[buf];
|
auto* buffer = (*model_->buffers())[buf];
|
||||||
auto* array = buffer->data();
|
auto* array = buffer->data();
|
||||||
return string(reinterpret_cast<const char*>(array->data()),
|
// Get the real length of the runtime string, since there might be
|
||||||
array->size());
|
// trailing
|
||||||
|
// '\0's in the buffer.
|
||||||
|
for (int len = 0; len < array->size(); ++len) {
|
||||||
|
if (array->data()[len] == '\0') {
|
||||||
|
return string(reinterpret_cast<const char*>(array->data()), len);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// If there is no '\0' in the buffer, this indicates that the flatbuffer
|
||||||
|
// is malformed.
|
||||||
|
TF_LITE_REPORT_ERROR(
|
||||||
|
error_reporter_,
|
||||||
|
"Min_runtime_version in model metadata is malformed");
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return "";
|
return "";
|
||||||
|
@ -366,7 +366,7 @@ TEST(BasicFlatBufferModel, TestReadRuntimeVersionFromModel) {
|
|||||||
"tensorflow/lite/testdata/test_min_runtime.bin");
|
"tensorflow/lite/testdata/test_min_runtime.bin");
|
||||||
ASSERT_TRUE(model2);
|
ASSERT_TRUE(model2);
|
||||||
// Check that we have read the runtime string correctly.
|
// Check that we have read the runtime string correctly.
|
||||||
ASSERT_EQ(model2->GetMinimumRuntime(), "1.10.0");
|
ASSERT_EQ(model2->GetMinimumRuntime(), "1.5.0");
|
||||||
}
|
}
|
||||||
|
|
||||||
// The test model has the following tensor encoded in the TACO format:
|
// The test model has the following tensor encoded in the TACO format:
|
||||||
|
BIN
tensorflow/lite/testdata/test_min_runtime.bin
vendored
BIN
tensorflow/lite/testdata/test_min_runtime.bin
vendored
Binary file not shown.
@ -32,7 +32,7 @@ cc_library(
|
|||||||
"//tensorflow/lite/schema:schema_fbs",
|
"//tensorflow/lite/schema:schema_fbs",
|
||||||
"//tensorflow/lite/toco:graph_transformations",
|
"//tensorflow/lite/toco:graph_transformations",
|
||||||
"//tensorflow/lite/toco:model",
|
"//tensorflow/lite/toco:model",
|
||||||
"//tensorflow/lite/tools/versioning:op_version",
|
"//tensorflow/lite/tools/versioning",
|
||||||
"@com_google_absl//absl/memory",
|
"@com_google_absl//absl/memory",
|
||||||
"@flatbuffers",
|
"@flatbuffers",
|
||||||
],
|
],
|
||||||
@ -147,6 +147,7 @@ cc_library(
|
|||||||
":operator",
|
":operator",
|
||||||
"//tensorflow/lite/toco:model",
|
"//tensorflow/lite/toco:model",
|
||||||
"//tensorflow/lite/toco:tooling_util",
|
"//tensorflow/lite/toco:tooling_util",
|
||||||
|
"//tensorflow/lite/tools/versioning",
|
||||||
"@com_google_absl//absl/strings",
|
"@com_google_absl//absl/strings",
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
|
@ -22,27 +22,13 @@ limitations under the License.
|
|||||||
#include "tensorflow/lite/toco/model.h"
|
#include "tensorflow/lite/toco/model.h"
|
||||||
#include "tensorflow/lite/toco/tflite/operator.h"
|
#include "tensorflow/lite/toco/tflite/operator.h"
|
||||||
#include "tensorflow/lite/toco/tooling_util.h"
|
#include "tensorflow/lite/toco/tooling_util.h"
|
||||||
|
#include "tensorflow/lite/tools/versioning/runtime_version.h"
|
||||||
|
|
||||||
namespace toco {
|
namespace toco {
|
||||||
namespace tflite {
|
namespace tflite {
|
||||||
|
|
||||||
bool CompareVersion(const string& v1, const string& v2) {
|
// Deprecated and please register new ops/versions in
|
||||||
const std::vector<string>& vec1 = absl::StrSplit(v1, '.');
|
// tflite/tools/versioning/op_version.cc".
|
||||||
const std::vector<string>& vec2 = absl::StrSplit(v2, '.');
|
|
||||||
int i = 0;
|
|
||||||
while (i < vec1.size() && i < vec2.size()) {
|
|
||||||
int v1_val, v2_val;
|
|
||||||
if (absl::SimpleAtoi(vec1[i], &v1_val) &&
|
|
||||||
absl::SimpleAtoi(vec2[i], &v2_val)) {
|
|
||||||
if (v1_val != v2_val) return v1_val < v2_val;
|
|
||||||
}
|
|
||||||
++i;
|
|
||||||
}
|
|
||||||
// If there are remaining items in v2 not being compared, then v1 should
|
|
||||||
// precede v2.
|
|
||||||
return i < vec2.size();
|
|
||||||
}
|
|
||||||
|
|
||||||
string GetMinimumRuntimeVersionForModel(const Model& model) {
|
string GetMinimumRuntimeVersionForModel(const Model& model) {
|
||||||
// Use this as the placeholder string if a particular op is not yet included
|
// Use this as the placeholder string if a particular op is not yet included
|
||||||
// in any Tensorflow's RC/Final release source package. Once that op is
|
// in any Tensorflow's RC/Final release source package. Once that op is
|
||||||
@ -253,7 +239,7 @@ string GetMinimumRuntimeVersionForModel(const Model& model) {
|
|||||||
// doesn't have a minimum runtime version associated, continue.
|
// doesn't have a minimum runtime version associated, continue.
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if (CompareVersion(model_min_version, it->second)) {
|
if (::tflite::CompareRuntimeVersion(model_min_version, it->second)) {
|
||||||
// Current min model runtime version should be bumped if we see a higher
|
// Current min model runtime version should be bumped if we see a higher
|
||||||
// op version.
|
// op version.
|
||||||
model_min_version = it->second;
|
model_min_version = it->second;
|
||||||
|
@ -20,11 +20,6 @@ limitations under the License.
|
|||||||
namespace toco {
|
namespace toco {
|
||||||
namespace tflite {
|
namespace tflite {
|
||||||
|
|
||||||
// Returns true if the first version string precedes the second.
|
|
||||||
// For example, '1.14' should precede '1.9', also '1.14.1' should precede
|
|
||||||
// '1.14'. If two version string is equal, then false will be returned.
|
|
||||||
bool CompareVersion(const string&, const string&);
|
|
||||||
|
|
||||||
// Get the minimum TF Lite runtime required to run a model. Each built-in
|
// Get the minimum TF Lite runtime required to run a model. Each built-in
|
||||||
// operator in the model will have its own minimum requirement of a runtime, and
|
// operator in the model will have its own minimum requirement of a runtime, and
|
||||||
// the model's minimum requirement of runtime is defined as the maximum of all
|
// the model's minimum requirement of runtime is defined as the maximum of all
|
||||||
|
@ -22,6 +22,7 @@ namespace toco {
|
|||||||
namespace tflite {
|
namespace tflite {
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
// TODO(b/150701120): port the tests to tools/versioning/op_version_test.cc.
|
||||||
TEST(OpVersionTest, MinimumVersionForSameOpVersions) {
|
TEST(OpVersionTest, MinimumVersionForSameOpVersions) {
|
||||||
Model model;
|
Model model;
|
||||||
// Float convolutional kernel is introduced since '1.5.0'.
|
// Float convolutional kernel is introduced since '1.5.0'.
|
||||||
@ -138,18 +139,6 @@ TEST(OpVersionTest, MinimumVersionForMixedOpVersions) {
|
|||||||
EXPECT_EQ(GetMinimumRuntimeVersionForModel(model), "1.10.0");
|
EXPECT_EQ(GetMinimumRuntimeVersionForModel(model), "1.10.0");
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST(OpVersionTest, CompareVersionString) {
|
|
||||||
EXPECT_TRUE(CompareVersion("1.9", "1.13"));
|
|
||||||
EXPECT_FALSE(CompareVersion("1.13", "1.13"));
|
|
||||||
EXPECT_TRUE(CompareVersion("1.14", "1.14.1"));
|
|
||||||
EXPECT_FALSE(CompareVersion("1.14.1", "1.14"));
|
|
||||||
EXPECT_FALSE(CompareVersion("1.14.1", "1.9"));
|
|
||||||
EXPECT_FALSE(CompareVersion("1.0.9", "1.0.8"));
|
|
||||||
EXPECT_FALSE(CompareVersion("2.1.0", "1.2.0"));
|
|
||||||
EXPECT_TRUE(CompareVersion("", "1.13"));
|
|
||||||
EXPECT_FALSE(CompareVersion("", ""));
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
} // namespace tflite
|
} // namespace tflite
|
||||||
} // namespace toco
|
} // namespace toco
|
||||||
|
@ -9,14 +9,20 @@ package(
|
|||||||
)
|
)
|
||||||
|
|
||||||
cc_library(
|
cc_library(
|
||||||
name = "op_version",
|
name = "versioning",
|
||||||
srcs = ["op_version.cc"],
|
srcs = [
|
||||||
|
"op_version.cc",
|
||||||
|
"runtime_version.cc",
|
||||||
|
],
|
||||||
hdrs = [
|
hdrs = [
|
||||||
"op_version.h",
|
"op_version.h",
|
||||||
|
"runtime_version.h",
|
||||||
],
|
],
|
||||||
deps = [
|
deps = [
|
||||||
"//tensorflow/core:tflite_portable_logging",
|
"//tensorflow/core:tflite_portable_logging",
|
||||||
|
"//tensorflow/lite:minimal_logging",
|
||||||
"//tensorflow/lite/kernels/internal:compatibility",
|
"//tensorflow/lite/kernels/internal:compatibility",
|
||||||
|
"//tensorflow/lite/schema:schema_fbs",
|
||||||
"//tensorflow/lite/schema:schema_fbs_with_mutable",
|
"//tensorflow/lite/schema:schema_fbs_with_mutable",
|
||||||
"@com_google_absl//absl/memory",
|
"@com_google_absl//absl/memory",
|
||||||
"@com_google_absl//absl/strings",
|
"@com_google_absl//absl/strings",
|
||||||
@ -25,10 +31,13 @@ cc_library(
|
|||||||
)
|
)
|
||||||
|
|
||||||
tf_cc_test(
|
tf_cc_test(
|
||||||
name = "op_version_test",
|
name = "versioning_test",
|
||||||
srcs = ["op_version_test.cc"],
|
srcs = [
|
||||||
|
"op_version_test.cc",
|
||||||
|
"runtime_version_test.cc",
|
||||||
|
],
|
||||||
deps = [
|
deps = [
|
||||||
":op_version",
|
":versioning",
|
||||||
"//tensorflow/lite/schema:schema_fbs_with_mutable",
|
"//tensorflow/lite/schema:schema_fbs_with_mutable",
|
||||||
"@com_google_googletest//:gtest_main",
|
"@com_google_googletest//:gtest_main",
|
||||||
],
|
],
|
||||||
|
285
tensorflow/lite/tools/versioning/runtime_version.cc
Normal file
285
tensorflow/lite/tools/versioning/runtime_version.cc
Normal file
@ -0,0 +1,285 @@
|
|||||||
|
/* Copyright 2020 The TensorFlow Authors. All Rights Reserved.
|
||||||
|
|
||||||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
you may not use this file except in compliance with the License.
|
||||||
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
Unless required by applicable law or agreed to in writing, software
|
||||||
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
See the License for the specific language governing permissions and
|
||||||
|
limitations under the License.
|
||||||
|
==============================================================================*/
|
||||||
|
#include "tensorflow/lite/tools/versioning/runtime_version.h"
|
||||||
|
|
||||||
|
#include <cstring>
|
||||||
|
|
||||||
|
#include "absl/strings/numbers.h"
|
||||||
|
#include "absl/strings/str_split.h"
|
||||||
|
#include "tensorflow/lite/minimal_logging.h"
|
||||||
|
#include "tensorflow/lite/schema/mutable/schema_generated.h"
|
||||||
|
|
||||||
|
namespace tflite {
|
||||||
|
|
||||||
|
bool CompareRuntimeVersion(const std::string& v1, const std::string& v2) {
|
||||||
|
const std::vector<std::string> vec1 = absl::StrSplit(v1, '.');
|
||||||
|
const std::vector<std::string> vec2 = absl::StrSplit(v2, '.');
|
||||||
|
int i = 0;
|
||||||
|
while (i < vec1.size() && i < vec2.size()) {
|
||||||
|
int v1_val, v2_val;
|
||||||
|
if (absl::SimpleAtoi(vec1[i], &v1_val) &&
|
||||||
|
absl::SimpleAtoi(vec2[i], &v2_val)) {
|
||||||
|
if (v1_val != v2_val) return v1_val < v2_val;
|
||||||
|
}
|
||||||
|
++i;
|
||||||
|
}
|
||||||
|
// If there are remaining items in v2 not being compared, then v1 should
|
||||||
|
// precede v2.
|
||||||
|
return i < vec2.size();
|
||||||
|
}
|
||||||
|
|
||||||
|
void UpdateMinimumRuntimeVersionForModel(uint8_t* model_buffer_pointer) {
|
||||||
|
// Use this as the placeholder string if a particular op is not yet included
|
||||||
|
// in any Tensorflow's RC/Final release source package. Once that op is
|
||||||
|
// included in the release, please update this with the real version string.
|
||||||
|
static constexpr char kPendingReleaseOpVersion[] = "UNKNOWN";
|
||||||
|
// A map from the version key of an op to its minimum runtime version.
|
||||||
|
// For example, {{kAveragePool, 1}, "1.5.0"}, means the 1st version of
|
||||||
|
// AveragePool requires a minimum TF Lite runtime version '1.5.0`.
|
||||||
|
static const std::map<std::pair<BuiltinOperator, int>, std::string>*
|
||||||
|
op_version_map =
|
||||||
|
new std::map<std::pair<BuiltinOperator, int>, std::string>({
|
||||||
|
{{BuiltinOperator_AVERAGE_POOL_2D, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_AVERAGE_POOL_2D, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_CONV_2D, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_CONV_2D, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_CONV_2D, 3}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_DEPTHWISE_CONV_2D, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_DEPTHWISE_CONV_2D, 2}, "1.12.0"},
|
||||||
|
{{BuiltinOperator_DEPTHWISE_CONV_2D, 3}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_ADD, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_ADD, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_ADD_N, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SPACE_TO_BATCH_ND, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_SPACE_TO_BATCH_ND, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SUB, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_SUB, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_DIV, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_BATCH_TO_SPACE_ND, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_BATCH_TO_SPACE_ND, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_CAST, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_CONCATENATION, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_CONCATENATION, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_DEPTH_TO_SPACE, 1}, "2.1.0"},
|
||||||
|
{{BuiltinOperator_FAKE_QUANT, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_FAKE_QUANT, 2}, "1.10.0"},
|
||||||
|
{{BuiltinOperator_FULLY_CONNECTED, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_FULLY_CONNECTED, 2}, "1.10.0"},
|
||||||
|
{{BuiltinOperator_FULLY_CONNECTED, 3}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_FULLY_CONNECTED, 4}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_FULLY_CONNECTED, 5}, "2.0.0"},
|
||||||
|
{{BuiltinOperator_FULLY_CONNECTED, 6}, "2.1.0"},
|
||||||
|
{{BuiltinOperator_GATHER, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_GATHER, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_GATHER, 3}, "1.15.0"},
|
||||||
|
{{BuiltinOperator_GATHER_ND, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SVDF, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_SVDF, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SVDF, 3}, "2.2.0"},
|
||||||
|
{{BuiltinOperator_L2_NORMALIZATION, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_L2_NORMALIZATION, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_L2_POOL_2D, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_LOCAL_RESPONSE_NORMALIZATION, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_MAX_POOL_2D, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_MAX_POOL_2D, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MAXIMUM, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MAXIMUM, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MINIMUM, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MINIMUM, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MUL, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_MUL, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MUL, 3}, "1.15.0"},
|
||||||
|
{{BuiltinOperator_PAD, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_PAD, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_TILE, 1}, "1.10.1"},
|
||||||
|
{{BuiltinOperator_TILE, 2}, "2.2.0"},
|
||||||
|
{{BuiltinOperator_PADV2, 1}, "1.9.0"},
|
||||||
|
{{BuiltinOperator_PADV2, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_RESHAPE, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_SOFTMAX, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_SOFTMAX, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SPACE_TO_DEPTH, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_SPACE_TO_DEPTH, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_TRANSPOSE, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_TRANSPOSE, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_TRANSPOSE, 3}, "1.15.0"},
|
||||||
|
{{BuiltinOperator_LSTM, 1}, "1.7.0"},
|
||||||
|
{{BuiltinOperator_LSTM, 2}, "1.10.0"},
|
||||||
|
{{BuiltinOperator_LSTM, 3}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_UNIDIRECTIONAL_SEQUENCE_LSTM, 1}, "1.13.1"},
|
||||||
|
{{BuiltinOperator_UNIDIRECTIONAL_SEQUENCE_LSTM, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_BIDIRECTIONAL_SEQUENCE_LSTM, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_BIDIRECTIONAL_SEQUENCE_RNN, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MEAN, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_MEAN, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SUM, 1}, "1.10.0"},
|
||||||
|
{{BuiltinOperator_SUM, 2}, "1.15.0"},
|
||||||
|
{{BuiltinOperator_REDUCE_MAX, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_REDUCE_MAX, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_REDUCE_MIN, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_REDUCE_MIN, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_REDUCE_PROD, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_REDUCE_ANY, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_RELU6, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_RELU6, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_RESIZE_BILINEAR, 1}, "1.7.0"},
|
||||||
|
{{BuiltinOperator_RESIZE_BILINEAR, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_RESIZE_BILINEAR, 3}, "2.2.0"},
|
||||||
|
{{BuiltinOperator_RESIZE_NEAREST_NEIGHBOR, 1}, "1.13.1"},
|
||||||
|
{{BuiltinOperator_RESIZE_NEAREST_NEIGHBOR, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SQUEEZE, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_SPLIT, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_SPLIT, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SPLIT, 3}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SPLIT_V, 1}, "1.13.1"},
|
||||||
|
{{BuiltinOperator_STRIDED_SLICE, 1}, "1.6.0"},
|
||||||
|
{{BuiltinOperator_STRIDED_SLICE, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_STRIDED_SLICE, 3}, "2.1.0"},
|
||||||
|
{{BuiltinOperator_TOPK_V2, 1}, "1.7.0"},
|
||||||
|
{{BuiltinOperator_TOPK_V2, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_ARG_MAX, 1}, "1.9.0"},
|
||||||
|
{{BuiltinOperator_ARG_MAX, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_ARG_MIN, 1}, "1.9.0"},
|
||||||
|
{{BuiltinOperator_ARG_MIN, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_TRANSPOSE_CONV, 1}, "1.9.0"},
|
||||||
|
{{BuiltinOperator_SPARSE_TO_DENSE, 1}, "1.9.0"},
|
||||||
|
{{BuiltinOperator_SPARSE_TO_DENSE, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SPARSE_TO_DENSE, 3}, "1.15.0"},
|
||||||
|
{{BuiltinOperator_EXPAND_DIMS, 1}, "1.10.0"},
|
||||||
|
{{BuiltinOperator_PACK, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_PACK, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SHAPE, 1}, "1.10.0"},
|
||||||
|
{{BuiltinOperator_SLICE, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SLICE, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SLICE, 3}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_TANH, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_TANH, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_ONE_HOT, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_UNPACK, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_UNPACK, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_UNPACK, 3}, "2.2.0"},
|
||||||
|
{{BuiltinOperator_LEAKY_RELU, 1}, "1.13.1"},
|
||||||
|
{{BuiltinOperator_LOGISTIC, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_LOGISTIC, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_LOG_SOFTMAX, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_LOG_SOFTMAX, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SQUARED_DIFFERENCE, 1}, "1.13.1"},
|
||||||
|
{{BuiltinOperator_MIRROR_PAD, 1}, "1.13.1"},
|
||||||
|
{{BuiltinOperator_UNIQUE, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_UNIDIRECTIONAL_SEQUENCE_RNN, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_WHERE, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_DEQUANTIZE, 1}, "1.13.1"},
|
||||||
|
{{BuiltinOperator_DEQUANTIZE, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_DEQUANTIZE, 3}, "1.15.0"},
|
||||||
|
{{BuiltinOperator_REVERSE_SEQUENCE, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_EQUAL, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_EQUAL, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_NOT_EQUAL, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_NOT_EQUAL, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_GREATER, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_GREATER, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_GREATER_EQUAL, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_GREATER_EQUAL, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_LESS, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_LESS, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_LESS_EQUAL, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_LESS_EQUAL, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SEGMENT_SUM, 1}, "2.2.0"},
|
||||||
|
{{BuiltinOperator_SELECT, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SELECT, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_SELECT_V2, 1}, "2.2.0"},
|
||||||
|
{{BuiltinOperator_FLOOR_DIV, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_FLOOR_DIV, 2}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_FLOOR, 1}, "1.9.0"},
|
||||||
|
{{BuiltinOperator_CEIL, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MATRIX_DIAG, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_MATRIX_SET_DIAG, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_ELU, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_ROUND, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_RELU, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_RELU, 2}, "2.1.0"},
|
||||||
|
{{BuiltinOperator_RELU_N1_TO_1, 1}, "1.5.0"},
|
||||||
|
{{BuiltinOperator_PRELU, 1}, "1.8.0"},
|
||||||
|
{{BuiltinOperator_EXP, 1}, "1.7.0"},
|
||||||
|
{{BuiltinOperator_COS, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_NEG, 1}, "1.9.0"},
|
||||||
|
{{BuiltinOperator_POW, 1}, "1.10.0"},
|
||||||
|
{{BuiltinOperator_LOGICAL_OR, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_LOGICAL_AND, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_LOGICAL_NOT, 1}, "1.11.0"},
|
||||||
|
{{BuiltinOperator_FLOOR_MOD, 1}, "1.13.0"},
|
||||||
|
{{BuiltinOperator_RANGE, 1}, "1.13.0"},
|
||||||
|
{{BuiltinOperator_SIN, 1}, "1.9.0"},
|
||||||
|
{{BuiltinOperator_LOG, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_RSQRT, 1}, "1.10.0"},
|
||||||
|
{{BuiltinOperator_SQUARE, 1}, "1.12.0"},
|
||||||
|
{{BuiltinOperator_ZEROS_LIKE, 1}, "1.12.0"},
|
||||||
|
{{BuiltinOperator_ABS, 1}, "1.13.0"},
|
||||||
|
{{BuiltinOperator_HARD_SWISH, 1}, "1.15.0"},
|
||||||
|
{{BuiltinOperator_FILL, 1}, "1.13.0"},
|
||||||
|
{{BuiltinOperator_REVERSE_V2, 1}, "1.14.0"},
|
||||||
|
{{BuiltinOperator_REVERSE_V2, 2}, "2.2.0"},
|
||||||
|
{{BuiltinOperator_RANK, 1}, "1.14.0"},
|
||||||
|
});
|
||||||
|
|
||||||
|
auto model = GetMutableModel(model_buffer_pointer);
|
||||||
|
std::string model_min_version;
|
||||||
|
auto subgraphs = model->subgraphs();
|
||||||
|
for (int i = 0; i < subgraphs->Length(); ++i) {
|
||||||
|
const SubGraph* subgraph = subgraphs->Get(i);
|
||||||
|
for (int j = 0; j < subgraph->operators()->Length(); ++j) {
|
||||||
|
const Operator* op = subgraph->operators()->Get(j);
|
||||||
|
const OperatorCode* op_code =
|
||||||
|
model->operator_codes()->Get(op->opcode_index());
|
||||||
|
std::pair<BuiltinOperator, int> version_key = {op_code->builtin_code(),
|
||||||
|
op_code->version()};
|
||||||
|
auto it = op_version_map->find(version_key);
|
||||||
|
if (it == op_version_map->end() ||
|
||||||
|
it->second == kPendingReleaseOpVersion) {
|
||||||
|
// In case we didn't find the current op in the map, or the operator
|
||||||
|
// doesn't have a minimum runtime version associated, continue.
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
if (CompareRuntimeVersion(model_min_version, it->second)) {
|
||||||
|
// Current min model runtime version should be bumped if we see a higher
|
||||||
|
// op version.
|
||||||
|
model_min_version = it->second;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// The size of the `min_runtime_version` metadata buffer is 16 bytes. If the
|
||||||
|
// generated `model_min_version` is equal or longer than 16 bytes, print a
|
||||||
|
// warning message and return.
|
||||||
|
if (model_min_version.size() >= 16) {
|
||||||
|
TFLITE_LOG(TFLITE_LOG_WARNING,
|
||||||
|
"Skip writing minimum runtime version string since it's "
|
||||||
|
"longer than 16 bytes.");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// Copy over the bytes from `model_min_version` into the buffer.
|
||||||
|
for (int i = 0; i < model->metadata()->size(); ++i) {
|
||||||
|
if (model->metadata()->Get(i)->name()->str() == "min_runtime_version") {
|
||||||
|
auto buffer = model->metadata()->Get(i)->buffer();
|
||||||
|
auto buffer_data =
|
||||||
|
model->mutable_buffers()->GetMutableObject(buffer)->mutable_data();
|
||||||
|
memset(buffer_data->data(), 0, buffer_data->size());
|
||||||
|
memcpy(buffer_data->data(), model_min_version.data(),
|
||||||
|
model_min_version.size());
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace tflite
|
33
tensorflow/lite/tools/versioning/runtime_version.h
Normal file
33
tensorflow/lite/tools/versioning/runtime_version.h
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
/* Copyright 2020 The TensorFlow Authors. All Rights Reserved.
|
||||||
|
|
||||||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
you may not use this file except in compliance with the License.
|
||||||
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
Unless required by applicable law or agreed to in writing, software
|
||||||
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
See the License for the specific language governing permissions and
|
||||||
|
limitations under the License.
|
||||||
|
==============================================================================*/
|
||||||
|
#ifndef TENSORFLOW_LITE_TOOLS_VERSIONING_RUNTIME_VERSION_H_
|
||||||
|
#define TENSORFLOW_LITE_TOOLS_VERSIONING_RUNTIME_VERSION_H_
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
#include "flatbuffers/flatbuffers.h" // TF:flatbuffers
|
||||||
|
|
||||||
|
namespace tflite {
|
||||||
|
// Update minimum runtime version of the given TFL flatbuffer model.
|
||||||
|
void UpdateMinimumRuntimeVersionForModel(uint8_t* model_buffer_pointer);
|
||||||
|
|
||||||
|
// Returns true if the first version string precedes the second.
|
||||||
|
// For example, '1.14' should precede '1.9', also '1.14.1' should precede
|
||||||
|
// '1.14'. If two version string is equal, then false will be returned.
|
||||||
|
bool CompareRuntimeVersion(const std::string&, const std::string&);
|
||||||
|
|
||||||
|
} // namespace tflite
|
||||||
|
|
||||||
|
#endif // TENSORFLOW_LITE_TOOLS_VERSIONING_RUNTIME_VERSION_H_
|
34
tensorflow/lite/tools/versioning/runtime_version_test.cc
Normal file
34
tensorflow/lite/tools/versioning/runtime_version_test.cc
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
/* Copyright 2020 The TensorFlow Authors. All Rights Reserved.
|
||||||
|
|
||||||
|
Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
you may not use this file except in compliance with the License.
|
||||||
|
You may obtain a copy of the License at
|
||||||
|
|
||||||
|
http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
|
||||||
|
Unless required by applicable law or agreed to in writing, software
|
||||||
|
distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
See the License for the specific language governing permissions and
|
||||||
|
limitations under the License.
|
||||||
|
==============================================================================*/
|
||||||
|
#include "tensorflow/lite/tools/versioning/runtime_version.h"
|
||||||
|
|
||||||
|
#include <gmock/gmock.h>
|
||||||
|
#include <gtest/gtest.h>
|
||||||
|
|
||||||
|
namespace tflite {
|
||||||
|
|
||||||
|
TEST(OpVersionTest, CompareRuntimeVersion) {
|
||||||
|
EXPECT_TRUE(CompareRuntimeVersion("1.9", "1.13"));
|
||||||
|
EXPECT_FALSE(CompareRuntimeVersion("1.13", "1.13"));
|
||||||
|
EXPECT_TRUE(CompareRuntimeVersion("1.14", "1.14.1"));
|
||||||
|
EXPECT_FALSE(CompareRuntimeVersion("1.14.1", "1.14"));
|
||||||
|
EXPECT_FALSE(CompareRuntimeVersion("1.14.1", "1.9"));
|
||||||
|
EXPECT_FALSE(CompareRuntimeVersion("1.0.9", "1.0.8"));
|
||||||
|
EXPECT_FALSE(CompareRuntimeVersion("2.1.0", "1.2.0"));
|
||||||
|
EXPECT_TRUE(CompareRuntimeVersion("", "1.13"));
|
||||||
|
EXPECT_FALSE(CompareRuntimeVersion("", ""));
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace tflite
|
Loading…
Reference in New Issue
Block a user