Skip to content

Commit 54bacc0

Browse files
committed
Handle missing data types. (#2984)
Summary: **Changes** - The runtime was failing if it encountered a datatype not supported by CoreML framework. The changes add support for all the datatypes that are supported by coremltools basically if `CoreMLBackend` can export a model then runtime would execute it. Complex types are not supported because `coremltools` doesn't support it. - Improves and cleans the multiarray copying code. - Adds portable ops to CoreML executor so that it can run a partitioned model. **Testing** - Tested partitioned model `coreml_stories.pte` - Added multiarray copying tests. Pull Request resolved: #2984 Reviewed By: kirklandsign Differential Revision: D56003795 Pulled By: shoumikhin fbshipit-source-id: fa1c7846f9510d68c359aed6761aedb2d10c6f46 (cherry picked from commit d731866)
1 parent 0ad7043 commit 54bacc0

29 files changed

+1277
-660
lines changed

backends/apple/coreml/CMakeLists.txt

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,8 @@ if(NOT EXECUTORCH_ROOT)
1313
set(EXECUTORCH_ROOT ${CMAKE_CURRENT_SOURCE_DIR}/../../..)
1414
endif()
1515

16+
option(COREML_BUILD_EXECUTOR_RUNNER "Build CoreML executor runner." OFF)
17+
1618
# inmemoryfs sources
1719
set(INMEMORYFS_SOURCES
1820
runtime/inmemoryfs/inmemory_filesystem.cpp
@@ -181,6 +183,14 @@ target_link_libraries(coremldelegate
181183
${SQLITE_LIBRARY}
182184
)
183185

186+
if(COREML_BUILD_EXECUTOR_RUNNER)
187+
target_link_libraries(coremldelegate
188+
PRIVATE
189+
portable_ops_lib
190+
portable_kernels
191+
)
192+
endif()
193+
184194
target_compile_options(coremldelegate PRIVATE "-fobjc-arc")
185195
target_compile_options(coremldelegate PRIVATE "-fno-exceptions")
186196

backends/apple/coreml/runtime/delegate/ETCoreMLAssetManager.mm

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -630,7 +630,7 @@ - (NSUInteger)_compact:(NSUInteger)sizeInBytes error:(NSError * __autoreleasing
630630
}
631631

632632
if (_estimatedSizeInBytes <= sizeInBytes) {
633-
return YES;
633+
return _estimatedSizeInBytes;
634634
}
635635

636636
std::error_code ec;

backends/apple/coreml/runtime/delegate/ETCoreMLDefaultModelExecutor.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,9 @@ __attribute__((objc_subclassing_restricted)) @interface ETCoreMLDefaultModelExec
2727
/// The model.
2828
@property (readonly, strong, nonatomic) ETCoreMLModel* model;
2929

30+
/// If set to `YES` then output backing are ignored.
31+
@property (readwrite, atomic) BOOL ignoreOutputBackings;
32+
3033
@end
3134

3235
NS_ASSUME_NONNULL_END

backends/apple/coreml/runtime/delegate/ETCoreMLDefaultModelExecutor.mm

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,9 @@ - (instancetype)initWithModel:(ETCoreMLModel *)model {
2626
loggingOptions:(const executorchcoreml::ModelLoggingOptions& __unused)loggingOptions
2727
eventLogger:(const executorchcoreml::ModelEventLogger* _Nullable __unused)eventLogger
2828
error:(NSError * __autoreleasing *)error {
29+
if (self.ignoreOutputBackings) {
30+
predictionOptions.outputBackings = @{};
31+
}
2932
id<MLFeatureProvider> outputs = [self.model.mlModel predictionFromFeatures:inputs
3033
options:predictionOptions
3134
error:error];

backends/apple/coreml/runtime/delegate/ETCoreMLLogging.h

Lines changed: 24 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77

88
#import <Foundation/Foundation.h>
99

10+
#import <executorch/runtime/platform/log.h>
1011
#import <os/log.h>
1112

1213
NS_ASSUME_NONNULL_BEGIN
@@ -48,7 +49,11 @@ typedef NS_ERROR_ENUM(ETCoreMLErrorDomain, ETCoreMLError) {
4849

4950
/// Record the error with `os_log_error` and fills `*errorOut` with `NSError`.
5051
#define ETCoreMLLogErrorAndSetNSError(errorOut, errorCode, formatString, ...) \
51-
os_log_error(ETCoreMLErrorUtils.loggingChannel, formatString, ##__VA_ARGS__); \
52+
if (ET_LOG_ENABLED) { \
53+
ET_LOG(Error, "%s", [NSString stringWithFormat:@formatString, ##__VA_ARGS__].UTF8String); \
54+
} else { \
55+
os_log_error(ETCoreMLErrorUtils.loggingChannel, formatString, ##__VA_ARGS__); \
56+
} \
5257
if (errorOut) { \
5358
*errorOut = \
5459
[NSError errorWithDomain:ETCoreMLErrorDomain \
@@ -58,24 +63,31 @@ typedef NS_ERROR_ENUM(ETCoreMLErrorDomain, ETCoreMLError) {
5863
}]; \
5964
}
6065

61-
/// Record the error and its underlying error with `os_log_error` and fills
62-
/// `*errorOut` with NSError.
66+
/// Record the error and its underlying error with `os_log_error` and fills `*errorOut` with `NSError`.
6367
#define ETCoreMLLogUnderlyingErrorAndSetNSError(errorOut, errorCode, underlyingNSError, formatString, ...) \
64-
os_log_error(ETCoreMLErrorUtils.loggingChannel, \
65-
formatString ", with underlying error= %@.", \
66-
##__VA_ARGS__, \
67-
(underlyingNSError).localizedDescription); \
68+
if (ET_LOG_ENABLED) { \
69+
ET_LOG(Error, "%s", [NSString stringWithFormat:@formatString, ##__VA_ARGS__].UTF8String); \
70+
} else { \
71+
os_log_error(ETCoreMLErrorUtils.loggingChannel, \
72+
formatString ", with underlying error= %@.", \
73+
##__VA_ARGS__, \
74+
(underlyingNSError).localizedDescription); \
75+
} \
6876
if (errorOut) { \
6977
*errorOut = [ETCoreMLErrorUtils errorWithCode:errorCode \
7078
underlyingError:underlyingNSError \
7179
format:@formatString, ##__VA_ARGS__]; \
7280
}
7381

74-
#define ETCoreMLLogError(error, formatString, ...) \
75-
os_log_error(ETCoreMLErrorUtils.loggingChannel, \
76-
formatString ", with error= %@.", \
77-
##__VA_ARGS__, \
78-
(error).localizedDescription);
82+
#define ETCoreMLLogError(error, formatString, ...) \
83+
if (ET_LOG_ENABLED) { \
84+
ET_LOG(Error, "%s", [NSString stringWithFormat:@formatString, ##__VA_ARGS__].UTF8String); \
85+
} else { \
86+
os_log_error(ETCoreMLErrorUtils.loggingChannel, \
87+
formatString ", with error= %@.", \
88+
##__VA_ARGS__, \
89+
(error).localizedDescription); \
90+
}
7991

8092

8193
#pragma clang diagnostic pop

backends/apple/coreml/runtime/delegate/ETCoreMLModel.h

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,12 +6,18 @@
66
// Please refer to the license found in the LICENSE file in the root directory of the source tree.
77

88
#import <CoreML/CoreML.h>
9+
#import <vector>
910

1011
NS_ASSUME_NONNULL_BEGIN
1112

1213
@class ETCoreMLAsset;
1314

15+
namespace executorchcoreml {
16+
class MultiArray;
17+
}
18+
1419
/// Represents a ML model, the class is a thin wrapper over `MLModel` with additional properties.
20+
__attribute__((objc_subclassing_restricted))
1521
@interface ETCoreMLModel : NSObject
1622

1723
- (instancetype)init NS_UNAVAILABLE;
@@ -31,6 +37,12 @@ NS_ASSUME_NONNULL_BEGIN
3137
orderedOutputNames:(NSOrderedSet<NSString*>*)orderedOutputNames
3238
error:(NSError* __autoreleasing*)error NS_DESIGNATED_INITIALIZER;
3339

40+
- (nullable NSArray<MLMultiArray*>*)prepareInputs:(const std::vector<executorchcoreml::MultiArray>&)inputs
41+
error:(NSError* __autoreleasing*)error;
42+
43+
- (nullable NSArray<MLMultiArray*>*)prepareOutputBackings:(const std::vector<executorchcoreml::MultiArray>&)outputs
44+
error:(NSError* __autoreleasing*)error;
45+
3446
/// The underlying MLModel.
3547
@property (strong, readonly, nonatomic) MLModel* mlModel;
3648

0 commit comments

Comments
 (0)