reader/spirv: Prevent nullptrs being passed to ast::CallExpression.
nullptrs are caused by errors. Detect and return before passing nullptrs to places they shouldn't go. Also: Rename 'params' to 'args'. These are arguments, not parameters. Bug: oss-fuzz:38074 Fixed: tint:1355 Change-Id: I77f97b4a8e5dab21802b300ba3eedad767ac2ad5 Reviewed-on: https://dawn-review.googlesource.com/c/tint/+/75425 Kokoro: Kokoro <noreply+kokoro@google.com> Reviewed-by: David Neto <dneto@google.com> Commit-Queue: Ben Clayton <bclayton@google.com>
This commit is contained in:
parent
5c99ed046a
commit
4a143a40a3
|
@ -5207,7 +5207,7 @@ const ast::Expression* FunctionEmitter::GetSamplerExpression(
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
ast::ExpressionList params;
|
ast::ExpressionList args;
|
||||||
const auto opcode = inst.opcode();
|
const auto opcode = inst.opcode();
|
||||||
|
|
||||||
// Form the texture operand.
|
// Form the texture operand.
|
||||||
|
@ -5215,13 +5215,13 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
if (!image) {
|
if (!image) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
params.push_back(GetImageExpression(inst));
|
args.push_back(GetImageExpression(inst));
|
||||||
|
|
||||||
// Form the sampler operand, if needed.
|
// Form the sampler operand, if needed.
|
||||||
if (IsSampledImageAccess(opcode)) {
|
if (IsSampledImageAccess(opcode)) {
|
||||||
// Form the sampler operand.
|
// Form the sampler operand.
|
||||||
if (auto* sampler = GetSamplerExpression(inst)) {
|
if (auto* sampler = GetSamplerExpression(inst)) {
|
||||||
params.push_back(sampler);
|
args.push_back(sampler);
|
||||||
} else {
|
} else {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -5247,7 +5247,7 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
if (coords.empty()) {
|
if (coords.empty()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
params.insert(params.end(), coords.begin(), coords.end());
|
args.insert(args.end(), coords.begin(), coords.end());
|
||||||
// Skip the coordinates operand.
|
// Skip the coordinates operand.
|
||||||
arg_index++;
|
arg_index++;
|
||||||
|
|
||||||
|
@ -5257,7 +5257,7 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
// the parameter list. Issues a diagnostic and returns false on error.
|
// the parameter list. Issues a diagnostic and returns false on error.
|
||||||
auto consume_dref = [&]() -> bool {
|
auto consume_dref = [&]() -> bool {
|
||||||
if (arg_index < num_args) {
|
if (arg_index < num_args) {
|
||||||
params.push_back(MakeOperand(inst, arg_index).expr);
|
args.push_back(MakeOperand(inst, arg_index).expr);
|
||||||
arg_index++;
|
arg_index++;
|
||||||
} else {
|
} else {
|
||||||
return Fail()
|
return Fail()
|
||||||
|
@ -5295,7 +5295,7 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
builtin_name = "textureGather";
|
builtin_name = "textureGather";
|
||||||
if (!texture_type->Is<DepthTexture>()) {
|
if (!texture_type->Is<DepthTexture>()) {
|
||||||
// The explicit component is the *first* argument in WGSL.
|
// The explicit component is the *first* argument in WGSL.
|
||||||
params.insert(params.begin(), ToI32(MakeOperand(inst, arg_index)).expr);
|
args.insert(args.begin(), ToI32(MakeOperand(inst, arg_index)).expr);
|
||||||
}
|
}
|
||||||
// Skip over the component operand, even for depth textures.
|
// Skip over the component operand, even for depth textures.
|
||||||
arg_index++;
|
arg_index++;
|
||||||
|
@ -5324,7 +5324,7 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
params.push_back(converted_texel);
|
args.push_back(converted_texel);
|
||||||
arg_index++;
|
arg_index++;
|
||||||
} else {
|
} else {
|
||||||
return Fail() << "image write is missing a Texel operand: "
|
return Fail() << "image write is missing a Texel operand: "
|
||||||
|
@ -5356,7 +5356,7 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
<< inst.PrettyPrint();
|
<< inst.PrettyPrint();
|
||||||
}
|
}
|
||||||
builtin_name += "Bias";
|
builtin_name += "Bias";
|
||||||
params.push_back(MakeOperand(inst, arg_index).expr);
|
args.push_back(MakeOperand(inst, arg_index).expr);
|
||||||
image_operands_mask ^= SpvImageOperandsBiasMask;
|
image_operands_mask ^= SpvImageOperandsBiasMask;
|
||||||
arg_index++;
|
arg_index++;
|
||||||
}
|
}
|
||||||
|
@ -5383,7 +5383,7 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
// Convert it to a signed integer type.
|
// Convert it to a signed integer type.
|
||||||
lod = ToI32(lod);
|
lod = ToI32(lod);
|
||||||
}
|
}
|
||||||
params.push_back(lod.expr);
|
args.push_back(lod.expr);
|
||||||
}
|
}
|
||||||
|
|
||||||
image_operands_mask ^= SpvImageOperandsLodMask;
|
image_operands_mask ^= SpvImageOperandsLodMask;
|
||||||
|
@ -5393,7 +5393,7 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
->IsAnyOf<DepthMultisampledTexture, MultisampledTexture>()) {
|
->IsAnyOf<DepthMultisampledTexture, MultisampledTexture>()) {
|
||||||
// textureLoad requires an explicit level-of-detail parameter for
|
// textureLoad requires an explicit level-of-detail parameter for
|
||||||
// non-multisampled texture types.
|
// non-multisampled texture types.
|
||||||
params.push_back(parser_impl_.MakeNullValue(ty_.I32()));
|
args.push_back(parser_impl_.MakeNullValue(ty_.I32()));
|
||||||
}
|
}
|
||||||
if (arg_index + 1 < num_args &&
|
if (arg_index + 1 < num_args &&
|
||||||
(image_operands_mask & SpvImageOperandsGradMask)) {
|
(image_operands_mask & SpvImageOperandsGradMask)) {
|
||||||
|
@ -5408,8 +5408,8 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
<< inst.PrettyPrint();
|
<< inst.PrettyPrint();
|
||||||
}
|
}
|
||||||
builtin_name += "Grad";
|
builtin_name += "Grad";
|
||||||
params.push_back(MakeOperand(inst, arg_index).expr);
|
args.push_back(MakeOperand(inst, arg_index).expr);
|
||||||
params.push_back(MakeOperand(inst, arg_index + 1).expr);
|
args.push_back(MakeOperand(inst, arg_index + 1).expr);
|
||||||
image_operands_mask ^= SpvImageOperandsGradMask;
|
image_operands_mask ^= SpvImageOperandsGradMask;
|
||||||
arg_index += 2;
|
arg_index += 2;
|
||||||
}
|
}
|
||||||
|
@ -5431,14 +5431,14 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
<< inst.PrettyPrint();
|
<< inst.PrettyPrint();
|
||||||
}
|
}
|
||||||
|
|
||||||
params.push_back(ToSignedIfUnsigned(MakeOperand(inst, arg_index)).expr);
|
args.push_back(ToSignedIfUnsigned(MakeOperand(inst, arg_index)).expr);
|
||||||
image_operands_mask ^= SpvImageOperandsConstOffsetMask;
|
image_operands_mask ^= SpvImageOperandsConstOffsetMask;
|
||||||
arg_index++;
|
arg_index++;
|
||||||
}
|
}
|
||||||
if (arg_index < num_args &&
|
if (arg_index < num_args &&
|
||||||
(image_operands_mask & SpvImageOperandsSampleMask)) {
|
(image_operands_mask & SpvImageOperandsSampleMask)) {
|
||||||
// TODO(dneto): only permitted with ImageFetch
|
// TODO(dneto): only permitted with ImageFetch
|
||||||
params.push_back(ToI32(MakeOperand(inst, arg_index)).expr);
|
args.push_back(ToI32(MakeOperand(inst, arg_index)).expr);
|
||||||
image_operands_mask ^= SpvImageOperandsSampleMask;
|
image_operands_mask ^= SpvImageOperandsSampleMask;
|
||||||
arg_index++;
|
arg_index++;
|
||||||
}
|
}
|
||||||
|
@ -5447,10 +5447,16 @@ bool FunctionEmitter::EmitImageAccess(const spvtools::opt::Instruction& inst) {
|
||||||
<< "): " << inst.PrettyPrint();
|
<< "): " << inst.PrettyPrint();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// If any of the arguments are nullptr, then we've failed.
|
||||||
|
if (std::any_of(args.begin(), args.end(),
|
||||||
|
[](auto* expr) { return expr == nullptr; })) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
auto* ident = create<ast::IdentifierExpression>(
|
auto* ident = create<ast::IdentifierExpression>(
|
||||||
Source{}, builder_.Symbols().Register(builtin_name));
|
Source{}, builder_.Symbols().Register(builtin_name));
|
||||||
auto* call_expr =
|
auto* call_expr =
|
||||||
create<ast::CallExpression>(Source{}, ident, std::move(params));
|
create<ast::CallExpression>(Source{}, ident, std::move(args));
|
||||||
|
|
||||||
if (inst.type_id() != 0) {
|
if (inst.type_id() != 0) {
|
||||||
// It returns a value.
|
// It returns a value.
|
||||||
|
|
Loading…
Reference in New Issue