Skip to content

Commit 903ec7c

Browse files
authored
fix overwrite builtin layer destruction (#4732)
* fix overwrite builtin layer destruction * make modelbin class copyable * test++
1 parent f893d24 commit 903ec7c

File tree

4 files changed

+109
-17
lines changed

4 files changed

+109
-17
lines changed

src/modelbin.cpp

+5
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,11 @@ ModelBin::~ModelBin()
2828
{
2929
}
3030

31+
Mat ModelBin::load(int /*w*/, int /*type*/) const
32+
{
33+
return Mat();
34+
}
35+
3136
Mat ModelBin::load(int w, int h, int type) const
3237
{
3338
Mat m = load(w * h, type);

src/modelbin.h

+1-1
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ class NCNN_EXPORT ModelBin
3131
// 2 = float16
3232
// 3 = int8
3333
// load vec
34-
virtual Mat load(int w, int type) const = 0;
34+
virtual Mat load(int w, int type) const;
3535
// load image
3636
virtual Mat load(int w, int h, int type) const;
3737
// load dim

src/net.cpp

+20-1
Original file line numberDiff line numberDiff line change
@@ -2025,7 +2025,26 @@ void Net::clear()
20252025
}
20262026
else
20272027
{
2028-
delete layer;
2028+
// check overwrite builtin layer destroyer
2029+
int index = -1;
2030+
const size_t overwrite_builtin_layer_registry_entry_count = d->overwrite_builtin_layer_registry.size();
2031+
for (size_t i = 0; i < overwrite_builtin_layer_registry_entry_count; i++)
2032+
{
2033+
if (d->overwrite_builtin_layer_registry[i].typeindex == layer->typeindex)
2034+
{
2035+
index = i;
2036+
break;
2037+
}
2038+
}
2039+
2040+
if (index != -1 && d->overwrite_builtin_layer_registry[index].destroyer)
2041+
{
2042+
d->overwrite_builtin_layer_registry[index].destroyer(layer, d->overwrite_builtin_layer_registry[index].userdata);
2043+
}
2044+
else
2045+
{
2046+
delete layer;
2047+
}
20292048
}
20302049
}
20312050
d->layers.clear();

tests/test_squeezenet.cpp

+83-15
Original file line numberDiff line numberDiff line change
@@ -241,25 +241,93 @@ static int test_squeezenet(const ncnn::Option& opt, int load_model_type, float e
241241
return check_top2(cls_scores, epsilon);
242242
}
243243

244-
class MySoftmax : public ncnn::Layer
244+
class MyConvolution : public ncnn::Layer
245245
{
246246
public:
247-
MySoftmax()
247+
MyConvolution()
248248
{
249-
one_blob_only = true;
250-
support_inplace = true;
249+
impl = ncnn::create_layer("Convolution");
250+
251+
one_blob_only = impl->one_blob_only;
252+
support_inplace = impl->support_inplace;
253+
254+
support_packing = impl->support_packing;
255+
support_vulkan = impl->support_vulkan;
256+
support_bf16_storage = impl->support_bf16_storage;
257+
support_fp16_storage = impl->support_fp16_storage;
258+
support_int8_storage = impl->support_int8_storage;
259+
support_image_storage = impl->support_image_storage;
260+
}
261+
262+
~MyConvolution()
263+
{
264+
delete impl;
265+
}
266+
267+
virtual int load_param(const ncnn::ParamDict& pd)
268+
{
269+
#if NCNN_VULKAN
270+
impl->vkdev = vkdev;
271+
#endif // NCNN_VULKAN
272+
273+
return impl->load_param(pd);
274+
}
275+
276+
virtual int load_model(const ncnn::ModelBin& mb)
277+
{
278+
return impl->load_model(mb);
279+
}
280+
281+
virtual int create_pipeline(const ncnn::Option& opt)
282+
{
283+
int ret = impl->create_pipeline(opt);
284+
285+
one_blob_only = impl->one_blob_only;
286+
support_inplace = impl->support_inplace;
287+
288+
support_packing = impl->support_packing;
289+
support_vulkan = impl->support_vulkan;
290+
support_bf16_storage = impl->support_bf16_storage;
291+
support_fp16_storage = impl->support_fp16_storage;
292+
support_int8_storage = impl->support_int8_storage;
293+
support_image_storage = impl->support_image_storage;
294+
295+
return ret;
296+
}
297+
298+
virtual int destroy_pipeline(const ncnn::Option& opt)
299+
{
300+
return impl->destroy_pipeline(opt);
301+
}
302+
303+
virtual int forward(const ncnn::Mat& bottom_blob, ncnn::Mat& top_blob, const ncnn::Option& opt) const
304+
{
305+
return impl->forward(bottom_blob, top_blob, opt);
306+
}
307+
308+
#if NCNN_VULKAN
309+
virtual int upload_model(ncnn::VkTransfer& cmd, const ncnn::Option& opt)
310+
{
311+
return impl->upload_model(cmd, opt);
251312
}
252313

253-
virtual int forward_inplace(ncnn::Mat& bottom_top_blob, const ncnn::Option& /*opt*/) const
314+
virtual int forward(const ncnn::VkMat& bottom_blob, ncnn::VkMat& top_blob, ncnn::VkCompute& cmd, const ncnn::Option& opt) const
254315
{
255-
bottom_top_blob.fill(0.f);
256-
bottom_top_blob[123] = 0.5f;
257-
bottom_top_blob[456] = 0.1f;
258-
return 0;
316+
return impl->forward(bottom_blob, top_blob, cmd, opt);
259317
}
318+
319+
virtual int forward(const ncnn::VkImageMat& bottom_blob, ncnn::VkImageMat& top_blob, ncnn::VkCompute& cmd, const ncnn::Option& opt) const
320+
{
321+
return impl->forward(bottom_blob, top_blob, cmd, opt);
322+
}
323+
#endif // NCNN_VULKAN
324+
325+
private:
326+
ncnn::Layer* impl;
260327
};
261328

262-
DEFINE_LAYER_CREATOR(MySoftmax)
329+
DEFINE_LAYER_CREATOR(MyConvolution)
330+
DEFINE_LAYER_DESTROYER(MyConvolution)
263331

264332
static int test_squeezenet_overwrite_softmax(const ncnn::Option& opt, int load_model_type, float epsilon = 0.001)
265333
{
@@ -279,7 +347,7 @@ static int test_squeezenet_overwrite_softmax(const ncnn::Option& opt, int load_m
279347
if (load_model_type == 0)
280348
{
281349
// load from plain model file
282-
squeezenet.register_custom_layer("Softmax", MySoftmax_layer_creator);
350+
squeezenet.register_custom_layer("Convolution", MyConvolution_layer_creator, MyConvolution_layer_destroyer);
283351
squeezenet.load_param(MODEL_DIR "/squeezenet_v1.1.param");
284352

285353
// test random feature disabled bits
@@ -296,7 +364,7 @@ static int test_squeezenet_overwrite_softmax(const ncnn::Option& opt, int load_m
296364
if (load_model_type == 1)
297365
{
298366
// load from plain model memory
299-
squeezenet.register_custom_layer("Softmax", MySoftmax_layer_creator);
367+
squeezenet.register_custom_layer("Convolution", MyConvolution_layer_creator, MyConvolution_layer_destroyer);
300368
param_str = read_file_string(MODEL_DIR "/squeezenet_v1.1.param");
301369
model_data = read_file_content(MODEL_DIR "/squeezenet_v1.1.bin");
302370
squeezenet.load_param_mem((const char*)param_str.c_str());
@@ -305,14 +373,14 @@ static int test_squeezenet_overwrite_softmax(const ncnn::Option& opt, int load_m
305373
if (load_model_type == 2)
306374
{
307375
// load from binary model file
308-
squeezenet.register_custom_layer(ncnn::layer_to_index("Softmax"), MySoftmax_layer_creator);
376+
squeezenet.register_custom_layer(ncnn::layer_to_index("Convolution"), MyConvolution_layer_creator, MyConvolution_layer_destroyer);
309377
squeezenet.load_param_bin(MODEL_DIR "/squeezenet_v1.1.param.bin");
310378
squeezenet.load_model(MODEL_DIR "/squeezenet_v1.1.bin");
311379
}
312380
if (load_model_type == 3)
313381
{
314382
// load from binary model memory
315-
squeezenet.register_custom_layer(ncnn::layer_to_index("Softmax"), MySoftmax_layer_creator);
383+
squeezenet.register_custom_layer(ncnn::layer_to_index("Convolution"), MyConvolution_layer_creator, MyConvolution_layer_destroyer);
316384
param_data = read_file_content(MODEL_DIR "/squeezenet_v1.1.param.bin");
317385
model_data = read_file_content(MODEL_DIR "/squeezenet_v1.1.bin");
318386
squeezenet.load_param((const unsigned char*)param_data);
@@ -345,7 +413,7 @@ static int test_squeezenet_overwrite_softmax(const ncnn::Option& opt, int load_m
345413
cls_scores[j] = out[j];
346414
}
347415

348-
return cls_scores[123] == 0.5f && cls_scores[456] == 0.1f ? 0 : -1;
416+
return check_top2(cls_scores, epsilon);
349417
}
350418

351419
int main()

0 commit comments

Comments
 (0)