Skip to content

AddInitializerToGraph ownership-semantics change in #28123 breaks C API callers (Chromium WebNN crash) #28782

@adrastogi

Description

@adrastogi

Describe the issue

#28123 looks like it has changed the ownership contract of the C API function OrtModelEditorApi::AddInitializerToGraph which is now causing a crash in Chromium WebNN scenarios.

OrtValue holds its tensor via std::shared_ptr data_.

Before that change, callers that passed a raw OrtValue* (e.g., via a unique-ptr-style wrapper's release()) handed off the owning reference; the graph's unique_ptr later destroyed it, dropping the shared_ptr refcount to 0 and firing any allocator-bound deleter (set via CreateTensorWithDataAndDeleterAsOrtValue).

After that change, ORT instead copies the OrtValue, sharing the data via shared_ptr refcount. The caller's released raw pointer is now leaked, and the deleter never fires; the leaked OrtValue keeps the refcount permanently above zero.

Chromium's ExternalWeightsManager class binds external-weight buffer destruction to the OrtValue's deleter via CreateTensorWithDataAndDeleterAsOrtValue. The deleter (FreeImpl) is the only thing that erases entries from the internal list.

With ORT after the change, the OrtValue gets leaked. The deleter never fires, the class's internal weight list is non-empty at teardown (which violates its post-condition), and so it aborts the process.

Code references:
https://source.chromium.org/chromium/chromium/src/+/main:services/webnn/ort/model_editor.cc;l=218
https://source.chromium.org/chromium/chromium/src/+/main:services/webnn/ort/external_weights_manager.cc;l=46

This crash did not occur with earlier versions of ONNX runtime.

To reproduce

  1. On a Chromium browser
  2. Create an ORT build at commit dbc55db or later.
  3. Launch with WebNN enabled (--enable-features=WebMachineLearningNeuralNetwork) on a page that builds and tears down a WebNN graph with constants ≥ 128 bytes (which routes through AddInitializerAsExternalData).
  4. On context teardown, the WebNN service crashes with CHECK failed: external_weights_.empty() (signature webnn::ort::ExternalWeightsManager::~ExternalWeightsManager).

I will see if I can also find a self-contained repro that is browser-agnostic.

Urgency

No response

Platform

Windows

OS Version

Windows 11

ONNX Runtime Installation

Built from Source

ONNX Runtime Version or Commit ID

dbc55db or later

ONNX Runtime API

C

Architecture

X64

Execution Provider

Other / Unknown

Execution Provider Library Version

No response

cc: @yuslepukhin

Metadata

Metadata

Assignees

Labels

ep:WebNNWebNN execution provider

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions