-
Notifications
You must be signed in to change notification settings - Fork 1
/
onnx2nnv.m
102 lines (93 loc) · 4.33 KB
/
onnx2nnv.m
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
function nn = onnx2nnv(onnxFile, loadOptions)
% nn = onnx2nnv(onnxFile, loadOptions)
% @nn: NNV's neural network
% @onnxFile: neural network to import in ONNX format
% @loadOptions (optional): see importONNXLayers.m for reference on optional arguments
% Import ONNX neural networks into NNV
% Output : NN -> NNV neural network class
%% Step 1. Load the network into MATLAB
switch nargin
% Only onnx network as input
case 1
try
net = importONNXNetwork(onnxFile, 'GenerateCustomLayers', false);
catch
warning('Using default options. Could not load the neural network with no custom layers');
% If error when no custom layer generation options, try setting
% input and output type, if still error, just load the layers
try
net = importONNXNetwork(onnxFile, 'GenerateCustomLayers', false, 'InputDataFormat', 'BSSC', 'OutputDataFormat', 'BC');
catch
try
net = importONNXLayers(onnxFile, 'InputDataFormat', 'BSSC', 'OutputDataFormat', 'BC', 'FoldConstants', "deep");
catch
try
net = importONNXLayers(onnxFile, 'OutputDataFormat', 'BC', 'FoldConstants', "deep");
catch
net = importONNXLayers(onnxFile);
end
end
end
end
% Onnx network + loading options as inputs (Parsing inputs)
case 2
if ~isstruct(loadOptions)
error('Wrong input type for input 2. loadOptions must be a struct.')
end
if isfield(loadOptions,'InputDataFormat')
InputDataFormat = loadOptions.InputDataFormat;
else
InputDataFormat = []; % automatically detected by impotONNXLayers
end
if isfield(loadOptions, 'OutputDataFormat')
OutputDataFormat = loadOptions.OutputDataFormat;
else
OutputDataFormat = []; % automatically detected by impotONNXLayers
end
if isfield(loadOptions, 'TargetNetwork')
targetNetwork = loadOptions.TargetNetwork;
else
targetNetwork = 'dagnetwork'; % default
end
if isfield(loadOptions, 'GenerateCustomLayers')
GenerateCustomLayers = loadOptions.GenerateCustomLayers;
else
GenerateCustomLayers = true;
end
if isfield(loadOptions, 'FoldConstants')
foldConstants = loadOptions.FoldConstants;
else
foldConstants = 'deep';
end
% Inputs has been parsed, now try loading the network
try
net = importONNXLayers(onnxFile, 'GenerateCustomLayers', GenerateCustomLayers, 'FoldConstants', foldConstants, ...
'TargetNetwork', targetNetwork, 'InputDataFormats', InputDataFormat, 'OutputDataFormats', OutputDataFormat);
catch
warning('Could not load the neural network with defined loading options. Trying default options for NNV.');
try
net = importONNXLayers(onnxFile, 'GenerateCustomLayers', false, 'InputDataFormat', 'BSSC', 'OutputDataFormat', 'BC');
catch
net = importONNXLayers(onnxFile, FoldConstants="deep");
end
end
end
% This function may not be perfect yet, we will define everything as a NN,
% return a succesful or unseccusful note, may even work with just the list
% of layers and connections. If fullyconnected (layer 1 -> layer 2, layer
% 2 -> layer 3, ...)
% The main function to be called will be importONNXLayers(...)
% There are different arguments to be passed in the onnx importers, please
% see importONNXNetwork and importONNXLayers for more info.
%% Step 2. Convert network into NNV format
nn = matlab2nnv(net); % Can use this separate function and add it to utils, or use a NN.parse function
%% Other notes
% Something more complicated but that may be more useful in the long term
% is directly using the function
% nnet.internal.cnn.onnx.ModelProto(Filename);
% found it inside nnet.internal.cnn.onnx.importONNXLayers.
% This returns the "raw" onnx model into matlab, then we can create the
% model ourselves.
% Cons: will be harder to debug, to understand. It will take longer to develop
% Pros: do not rely on MATLAB to add support to some of these operations, should be more robust
end