Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add missing validation steps for several ops #820

Merged
merged 2 commits into from
Feb 22, 2025
Merged
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 28 additions & 7 deletions index.bs
Original file line number Diff line number Diff line change
Expand Up @@ -2658,15 +2658,19 @@ partial dictionary MLOpSupportLimits {
1. If |options|.{{MLConv2dOptions/bias}} [=map/exists=]:
1. If its [=MLOperand/shape=] is not [=list/equal=] to « |outputChannels| », then [=exception/throw=] a {{TypeError}}.
1. If its [=MLOperand/dataType=] is not one of its [=/allowed data types=] (according to [this table](#constraints-conv2d)), then [=exception/throw=] a {{TypeError}}.
1. Let |outputSizes| be the result of [=MLGraphBuilder/calculating conv2d output sizes=] given |inputHeight|, |inputWidth|, |filterHeight|, |filterWidth|, |options|.{{MLConv2dOptions/padding}}, |options|.{{MLConv2dOptions/strides}}, and |options|.{{MLConv2dOptions/dilations}}.
1. Let « |outputHeight|, |outputWidth| » be the result of [=MLGraphBuilder/calculating conv2d output sizes=] given |inputHeight|, |inputWidth|, |filterHeight|, |filterWidth|, |options|.{{MLConv2dOptions/padding}}, |options|.{{MLConv2dOptions/strides}}, and |options|.{{MLConv2dOptions/dilations}}.
1. If either |outputHeight| or |outputWidth| is not a [=valid dimension=], then [=exception/throw=] a {{TypeError}}.
1. Switch on |options|.{{MLConv2dOptions/inputLayout}}:
<dl class=switch>
: {{MLInputOperandLayout/"nchw"}}
:: Let |outputShape| be « |batches|, |outputChannels|, floor( |outputSizes|[0] ), floor( |outputSizes|[1] ) ».
:: Let |outputShape| be « |batches|, |outputChannels|, floor( |outputHeight| ), floor( |outputWidth| ) ».
: {{MLInputOperandLayout/"nhwc"}}
:: Let |outputShape| be « |batches|, floor( |outputSizes|[0] ), floor( |outputSizes|[1] ), |outputChannels| ».
:: Let |outputShape| be « |batches|, floor( |outputHeight| ), floor( |outputWidth| ), |outputChannels| ».
</dl>
1. If any [=list/item=] in |outputShape| is not a [=valid dimension=], then [=exception/throw=] a {{TypeError}}.

Issue: The preceding step appears redundant with the validation of |outputHeight| and |outputWidth| above. Remove it?

1. Let |desc| be the result of [=creating an MLOperandDescriptor=] given |input|'s [=MLOperand/dataType=] and |outputShape|.
1. *Make graph connections:*
1. Let |output| be the result of [=creating an MLOperand=] given [=this=] and |desc|.
Expand Down Expand Up @@ -2852,6 +2856,10 @@ partial dictionary MLOpSupportLimits {
1. Otherwise, if |options|.{{MLConvTranspose2dOptions/outputPadding}}'s [=list/size=] is not 2, then [=exception/throw=] a {{TypeError}}.
1. If |options|.{{MLConvTranspose2dOptions/outputSizes}} [=map/exists=]:
1. If its [=list/size=] is not 2, then [=exception/throw=] a {{TypeError}}.
1. If any of its [=list/items=] is not a [=valid dimension=], then [=exception/throw=] a {{TypeError}}.

Issue: The preceding step appears redundant with the validation of |outputHeight| and |outputWidth| below. Remove it?
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

sgtm

But I suppose we still need to validate the user-supplied output size according to stride and calculated output size which is computed by ignoring output padding, and ensure the user-supplied output size satisfying

calculated output size <= user-supplied output size < calculated output size + stride

like Chromium impl does: https://source.chromium.org/chromium/chromium/src/+/main:services/webnn/public/cpp/graph_validation_utils.cc;l=782;drc=8636bb104c0e28b695adfe050dd1b70bfe05cdc8

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Removed the step (and issue), added that validation in a0ab8c7 - please verify?


1. Otherwise:
1. If |options|.{{MLConvTranspose2dOptions/outputPadding}}[0] is greater than or equal to |options|.{{MLConvTranspose2dOptions/strides}}[0], or |options|.{{MLConvTranspose2dOptions/outputPadding}}[1] is greater than or equal to |options|.{{MLConvTranspose2dOptions/strides}}[1], then [=exception/throw=] a {{TypeError}}.
1. If |options|.{{MLConvTranspose2dOptions/groups}} is 0, then [=exception/throw=] a {{TypeError}}.
Expand Down Expand Up @@ -2884,6 +2892,7 @@ partial dictionary MLOpSupportLimits {
1. Otherwise:
1. Let |outputHeight| be the result of [=MLGraphBuilder/calculating convtranspose output size=] given |inputHeight|, |filterHeight|, |padding|[0], |padding|[1], |strides|[0], |dilations|[0], and |outputPadding|[0].
1. Let |outputWidth| be the result of [=MLGraphBuilder/calculating convtranspose output size=] given |inputWidth|, |filterWidth|, |padding|[2], |padding|[3], |strides|[1], |dilations|[1] and |outputPadding|[1].
1. If either |outputHeight| or |outputWidth| is not a [=valid dimension=], then [=exception/throw=] a {{TypeError}}.
1. Switch on |options|.{{MLConvTranspose2dOptions/inputLayout}}:
<dl class=switch>
: {{MLInputOperandLayout/"nchw"}}
Expand All @@ -2892,6 +2901,9 @@ partial dictionary MLOpSupportLimits {
:: Let |outputShape| be « |batches|, floor( |outputHeight| ), floor( |outputWidth| ), |outputChannels| ».
</dl>
1. If any [=list/item=] in |outputShape| is not a [=valid dimension=], then [=exception/throw=] a {{TypeError}}.

Issue: The preceding step appears redundant with the validation of |outputHeight| and |outputWidth| above. Remove it?
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

outputChannels is calculated by step

Let |outputChannels| be |filterOutputChannels| * |options|.{{MLConvTranspose2dOptions/groups}}.

We may need to validate it right after that step? Like Chromium impl does: https://source.chromium.org/chromium/chromium/src/+/main:services/webnn/public/cpp/graph_validation_utils.cc;l=747;drc=8636bb104c0e28b695adfe050dd1b70bfe05cdc8

Copy link
Member Author

@inexorabletash inexorabletash Feb 21, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point. Added validation in a0ab8c7. Please verify?


1. Let |desc| be the result of [=creating an MLOperandDescriptor=] given |input|'s [=MLOperand/dataType=] and |outputShape|.
1. *Make graph connections:*
1. Let |output| be the result of [=creating an MLOperand=] given [=this=] and |desc|.
Expand Down Expand Up @@ -5602,6 +5614,7 @@ partial dictionary MLOpSupportLimits {
1. Let |numDirections| be 2 if |options|.{{MLLstmOptions/direction}} is {{MLRecurrentNetworkDirection/"both"}}, or 1 otherwise.
1. If the [=MLOperand/dataType=] of any of |input|, |weight| or |recurrentWeight| is not one of its [=/allowed data types=] (according to [this table](#constraints-lstm)), then [=exception/throw=] a {{TypeError}}.
1. If the [=MLOperand/rank=] of any of |input|, |weight| or |recurrentWeight| is not its [=/allowed rank=], then [=exception/throw=] a {{TypeError}}.
1. If |steps| is 0, then [=exception/throw=] a {{TypeError}}.
1. If |input|'s [=MLOperand/shape=][0] is not equal to |steps|, then [=exception/throw=] a {{TypeError}}.
1. Let |batchSize| be |input|'s [=MLOperand/shape=][1].
1. Let |inputSize| be |input|'s [=MLOperand/shape=][2].
Expand Down Expand Up @@ -6547,6 +6560,7 @@ partial dictionary MLOpSupportLimits {
</dl>
1. If |options|.{{MLPool2dOptions/windowDimensions}} does not [=map/exist=], set |options|.{{MLPool2dOptions/windowDimensions}} to « |inputHeight|, |inputWidth| ».
1. If |options|.{{MLPool2dOptions/windowDimensions}}'s [=list/size=] is not 2, then [=exception/throw=] a {{TypeError}}.
1. If any [=list/item=] in |options|.{{MLPool2dOptions/windowDimensions}} is equal to 0, then [=exception/throw=] a {{TypeError}}.
1. If |options|.{{MLPool2dOptions/outputSizes}} [=map/exists=], or if |options|.{{MLPool2dOptions/padding}} does not [=map/exist=], set |options|.{{MLPool2dOptions/padding}} to the [=/list=] « 0, 0, 0, 0 ».
1. If |options|.{{MLPool2dOptions/padding}}'s [=list/size=] is not 4, then [=exception/throw=] a {{TypeError}}.
1. If |options|.{{MLPool2dOptions/strides}} does not [=map/exist=], set |options|.{{MLPool2dOptions/strides}} to the [=/list=] « 1, 1 ».
Expand All @@ -6560,11 +6574,13 @@ partial dictionary MLOpSupportLimits {
1. If any value in |options|.{{MLPool2dOptions/dilations}} is not greater than 0, then [=exception/throw=] a {{TypeError}}.
1. Let |desc| be a copy of |input|.{{MLOperand/[[descriptor]]}}.
1. *Calculate the output shape:*
1. If |options|.{{MLPool2dOptions/outputSizes}} [=map/exists=], then let « |outputHeight|, |outputWidth| » be |options|.{{MLPool2dOptions/outputSizes}}.
1. Let « |windowHeight|, |windowWidth| » be |options|.{{MLPool2dOptions/windowDimensions}}.
1. Let « |calculatedOutputHeight|, |calculatedOutputWidth| » be the result of [=MLGraphBuilder/calculating conv2d output sizes=] given |inputHeight|, |inputWidth|, |windowHeight|, |windowWidth|, |options|.{{MLPool2dOptions/padding}}, |options|.{{MLPool2dOptions/strides}}, and |options|.{{MLPool2dOptions/dilations}}.
1. If |options|.{{MLPool2dOptions/outputSizes}} [=map/exists=], then:
1. Let « |outputHeight|, |outputWidth| » be |options|.{{MLPool2dOptions/outputSizes}}.
1. If neither |outputHeight| equals floor( |calculatedOutputHeight| ) and |outputWidth| equals floor( |calculatedOutputWidth| ), nor |outputHeight| equals ceil( |calculatedOutputHeight| ) and |outputWidth| equals ceil( |calculatedOutputWidth| ), then [=exception/throw=] a {{TypeError}}.
1. Otherwise:
1. Let « |windowHeight|, |windowWidth| » be |options|.{{MLPool2dOptions/windowDimensions}}.
1. Let |outputSizes| be the result of [=MLGraphBuilder/calculating conv2d output sizes=] given |inputHeight|, |inputWidth|, |windowHeight|, |windowWidth|, |options|.{{MLPool2dOptions/padding}}, |options|.{{MLPool2dOptions/strides}}, and |options|.{{MLPool2dOptions/dilations}}.
1. Let « |outputHeight|, |outputWidth| » be |outputSizes|.
1. Let « |outputHeight|, |outputWidth| » be « |calculatedOutputHeight|, |calculatedOutputWidth| ».
1. Switch on |options|.{{MLPool2dOptions/roundingType}}:
<dl class=switch>
: {{MLRoundingType/"floor"}}
Expand All @@ -6576,6 +6592,7 @@ partial dictionary MLOpSupportLimits {
1. Set |outputWidth| to ceiling(|outputWidth|).
1. Set |outputHeight| to ceiling(|outputHeight|).
</dl>
1. If either |outputHeight| or |outputWidth| is not a [=valid dimension=], then [=exception/throw=] a {{TypeError}}.
1. Switch on |options|.{{MLPool2dOptions/layout}}:
<dl class=switch>
: {{MLInputOperandLayout/"nchw"}}
Expand All @@ -6584,6 +6601,9 @@ partial dictionary MLOpSupportLimits {
:: Let |outputShape| be « |batches|, |outputHeight|, |outputWidth|, |channels| ».
</dl>
1. If any [=list/item=] in |outputShape| is not a [=valid dimension=], then [=exception/throw=] a {{TypeError}}.

Issue: The preceding step appears redundant with the validation of |outputHeight| and |outputWidth| above. Remove it?

1. Set |desc|.{{MLOperandDescriptor/shape}} to |outputShape|.
1. *Make graph connections:*
1. Let |output| be the result of [=creating an MLOperand=] given [=this=] and |desc|.
Expand Down Expand Up @@ -7816,6 +7836,7 @@ partial dictionary MLOpSupportLimits {
1. Let |axis| be |options|.{{MLSplitOptions/axis}}.
1. If |axis| is greater than or equal to |input|'s [=MLOperand/rank=], then [=exception/throw=] a {{TypeError}}.
1. If |splits| is an {{unsigned long}}:
1. If |splits| is 0, then [=exception/throw=] a {{TypeError}}.
1. If |input|'s [=MLOperand/shape=][|axis|] % |splits| is not 0, then [=exception/throw=] a {{TypeError}}.
1. Otherwise, let |splitCount| be |splits|.
1. If |splits| is a [=sequence=]<{{unsigned long}}>:
Expand Down
Loading