mirror of
https://github.com/github/codeql.git
synced 2026-02-11 20:51:06 +01:00
Merge pull request #21168 from hvitved/rust/type-inference-remove-blanket-constraint-restriction
Rust: Remove restriction that blanket(-like) impls must have a constraint
This commit is contained in:
@@ -5,7 +5,10 @@
|
||||
private import rust
|
||||
private import codeql.rust.Concepts
|
||||
private import codeql.rust.dataflow.DataFlow
|
||||
private import codeql.rust.dataflow.FlowSummary
|
||||
private import codeql.rust.internal.PathResolution
|
||||
private import codeql.rust.internal.typeinference.Type
|
||||
private import codeql.rust.internal.typeinference.TypeMention
|
||||
|
||||
/**
|
||||
* A call to the `starts_with` method on a `Path`.
|
||||
@@ -19,6 +22,34 @@ private class StartswithCall extends Path::SafeAccessCheck::Range, MethodCall {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* A flow summary for the [reflexive implementation of the `From` trait][1].
|
||||
*
|
||||
* Blanket implementations currently don't have a canonical path, so we cannot
|
||||
* use models-as-data for this model.
|
||||
*
|
||||
* [1]: https://doc.rust-lang.org/std/convert/trait.From.html#impl-From%3CT%3E-for-T
|
||||
*/
|
||||
private class ReflexiveFrom extends SummarizedCallable::Range {
|
||||
ReflexiveFrom() {
|
||||
exists(ImplItemNode impl |
|
||||
impl.resolveTraitTy().(Trait).getCanonicalPath() = "core::convert::From" and
|
||||
this = impl.getAssocItem("from") and
|
||||
resolvePath(this.getParam(0).getTypeRepr().(PathTypeRepr).getPath()) =
|
||||
impl.getBlanketImplementationTypeParam()
|
||||
)
|
||||
}
|
||||
|
||||
override predicate propagatesFlow(
|
||||
string input, string output, boolean preservesValue, string model
|
||||
) {
|
||||
input = "Argument[0]" and
|
||||
output = "ReturnValue" and
|
||||
preservesValue = true and
|
||||
model = "ReflexiveFrom"
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* The [`Option` enum][1].
|
||||
*
|
||||
|
||||
@@ -126,7 +126,7 @@ module SatisfiesBlanketConstraint<
|
||||
|
||||
/**
|
||||
* Holds if the argument type `at` satisfies the first non-trivial blanket
|
||||
* constraint of `impl`.
|
||||
* constraint of `impl`, or if there are no non-trivial constraints of `impl`.
|
||||
*/
|
||||
pragma[nomagic]
|
||||
predicate satisfiesBlanketConstraint(ArgumentType at, ImplItemNode impl) {
|
||||
@@ -135,6 +135,11 @@ module SatisfiesBlanketConstraint<
|
||||
SatisfiesBlanketConstraintInput::relevantConstraint(ato, impl, traitBound) and
|
||||
SatisfiesBlanketConstraint::satisfiesConstraintType(ato, TTrait(traitBound), _, _)
|
||||
)
|
||||
or
|
||||
exists(TypeParam blanketTypeParam |
|
||||
hasBlanketCandidate(at, impl, _, blanketTypeParam) and
|
||||
not hasFirstNonTrivialTraitBound(blanketTypeParam, _)
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -35,6 +35,12 @@ private predicate implSiblingCandidate(
|
||||
rootType = selfTy.resolveType()
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate blanketImplSiblingCandidate(ImplItemNode impl, Trait trait) {
|
||||
impl.isBlanketImplementation() and
|
||||
trait = impl.resolveTraitTy()
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if `impl1` and `impl2` are a sibling implementations of `trait`. We
|
||||
* consider implementations to be siblings if they implement the same trait for
|
||||
@@ -44,17 +50,22 @@ private predicate implSiblingCandidate(
|
||||
*/
|
||||
pragma[inline]
|
||||
private predicate implSiblings(TraitItemNode trait, Impl impl1, Impl impl2) {
|
||||
exists(Type rootType, TypeMention selfTy1, TypeMention selfTy2 |
|
||||
impl1 != impl2 and
|
||||
implSiblingCandidate(impl1, trait, rootType, selfTy1) and
|
||||
implSiblingCandidate(impl2, trait, rootType, selfTy2) and
|
||||
// In principle the second conjunct below should be superflous, but we still
|
||||
// have ill-formed type mentions for types that we don't understand. For
|
||||
// those checking both directions restricts further. Note also that we check
|
||||
// syntactic equality, whereas equality up to renaming would be more
|
||||
// correct.
|
||||
typeMentionEqual(selfTy1, selfTy2) and
|
||||
typeMentionEqual(selfTy2, selfTy1)
|
||||
impl1 != impl2 and
|
||||
(
|
||||
exists(Type rootType, TypeMention selfTy1, TypeMention selfTy2 |
|
||||
implSiblingCandidate(impl1, trait, rootType, selfTy1) and
|
||||
implSiblingCandidate(impl2, trait, rootType, selfTy2) and
|
||||
// In principle the second conjunct below should be superflous, but we still
|
||||
// have ill-formed type mentions for types that we don't understand. For
|
||||
// those checking both directions restricts further. Note also that we check
|
||||
// syntactic equality, whereas equality up to renaming would be more
|
||||
// correct.
|
||||
typeMentionEqual(selfTy1, selfTy2) and
|
||||
typeMentionEqual(selfTy2, selfTy1)
|
||||
)
|
||||
or
|
||||
blanketImplSiblingCandidate(impl1, trait) and
|
||||
blanketImplSiblingCandidate(impl2, trait)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -63,7 +74,7 @@ private predicate implSiblings(TraitItemNode trait, Impl impl1, Impl impl2) {
|
||||
* exists for the same type.
|
||||
*/
|
||||
pragma[nomagic]
|
||||
private predicate implHasSibling(Impl impl, Trait trait) { implSiblings(trait, impl, _) }
|
||||
private predicate implHasSibling(ImplItemNode impl, Trait trait) { implSiblings(trait, impl, _) }
|
||||
|
||||
/**
|
||||
* Holds if type parameter `tp` of `trait` occurs in the function `f` with the name
|
||||
|
||||
@@ -356,7 +356,7 @@ module ArgsAreInstantiationsOf<ArgsAreInstantiationsOfInputSig Input> {
|
||||
string toString() { result = call.toString() + " [arg " + pos + "]" }
|
||||
}
|
||||
|
||||
private module ArgIsInstantiationOfInput implements
|
||||
private module ArgIsInstantiationOfToIndexInput implements
|
||||
IsInstantiationOfInputSig<CallAndPos, AssocFunctionType>
|
||||
{
|
||||
pragma[nomagic]
|
||||
@@ -389,7 +389,7 @@ module ArgsAreInstantiationsOf<ArgsAreInstantiationsOfInputSig Input> {
|
||||
}
|
||||
|
||||
private module ArgIsInstantiationOfToIndex =
|
||||
ArgIsInstantiationOf<CallAndPos, ArgIsInstantiationOfInput>;
|
||||
ArgIsInstantiationOf<CallAndPos, ArgIsInstantiationOfToIndexInput>;
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate argsAreInstantiationsOfToIndex(
|
||||
@@ -413,4 +413,24 @@ module ArgsAreInstantiationsOf<ArgsAreInstantiationsOfInputSig Input> {
|
||||
rnk = max(int r | toCheckRanked(i, f, _, r))
|
||||
)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
private predicate argsAreNotInstantiationsOf0(
|
||||
Input::Call call, FunctionPosition pos, ImplOrTraitItemNode i
|
||||
) {
|
||||
ArgIsInstantiationOfToIndex::argIsNotInstantiationOf(MkCallAndPos(call, pos), i, _, _)
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if _some_ argument of `call` has a type that is not an instantiation of the
|
||||
* type of the corresponding parameter of `f` inside `i`.
|
||||
*/
|
||||
pragma[nomagic]
|
||||
predicate argsAreNotInstantiationsOf(Input::Call call, ImplOrTraitItemNode i, Function f) {
|
||||
exists(FunctionPosition pos |
|
||||
argsAreNotInstantiationsOf0(call, pos, i) and
|
||||
call.hasTargetCand(i, f) and
|
||||
Input::toCheck(i, f, pos, _)
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1289,6 +1289,13 @@ private class BorrowKind extends TBorrowKind {
|
||||
}
|
||||
}
|
||||
|
||||
// for now, we do not handle ambiguous targets when one of the types is itself
|
||||
// a constrained type parameter; we should be checking the constraints in this case
|
||||
private predicate typeCanBeUsedForDisambiguation(Type t) {
|
||||
not t instanceof TypeParameter or
|
||||
t.(TypeParamTypeParameter).getTypeParam() = any(TypeParam tp | not tp.hasTypeBound())
|
||||
}
|
||||
|
||||
/**
|
||||
* Provides logic for resolving calls to methods.
|
||||
*
|
||||
@@ -2234,7 +2241,8 @@ private module MethodResolution {
|
||||
methodCallBlanketLikeCandidate(mc, _, impl, _, blanketPath, blanketTypeParam) and
|
||||
// Only apply blanket implementations when no other implementations are possible;
|
||||
// this is to account for codebases that use the (unstable) specialization feature
|
||||
// (https://rust-lang.github.io/rfcs/1210-impl-specialization.html)
|
||||
// (https://rust-lang.github.io/rfcs/1210-impl-specialization.html), as well as
|
||||
// cases where our blanket implementation filtering is not precise enough.
|
||||
(mcc.hasNoCompatibleNonBlanketTarget() or not impl.isBlanketImplementation())
|
||||
|
|
||||
borrow.isNoBorrow()
|
||||
@@ -2384,10 +2392,7 @@ private module MethodResolution {
|
||||
exists(TypePath path, Type t0 |
|
||||
FunctionOverloading::functionResolutionDependsOnArgument(i, f, pos, path, t0) and
|
||||
t.appliesTo(f, i, pos) and
|
||||
// for now, we do not handle ambiguous targets when one of the types it iself
|
||||
// a type parameter; we should be checking the constraints on that type parameter
|
||||
// in this case
|
||||
not t0 instanceof TypeParameter
|
||||
typeCanBeUsedForDisambiguation(t0)
|
||||
)
|
||||
}
|
||||
|
||||
@@ -2746,7 +2751,7 @@ private module NonMethodResolution {
|
||||
* Gets the blanket function that this call may resolve to, if any.
|
||||
*/
|
||||
pragma[nomagic]
|
||||
private NonMethodFunction resolveCallTargetBlanketCand(ImplItemNode impl) {
|
||||
NonMethodFunction resolveCallTargetBlanketCand(ImplItemNode impl) {
|
||||
exists(string name |
|
||||
this.hasNameAndArity(pragma[only_bind_into](name), _) and
|
||||
ArgIsInstantiationOfBlanketParam::argIsInstantiationOf(MkCallAndBlanketPos(this, _), impl, _) and
|
||||
@@ -2761,12 +2766,11 @@ private module NonMethodResolution {
|
||||
predicate hasTrait() { exists(this.getTrait()) }
|
||||
|
||||
pragma[nomagic]
|
||||
NonMethodFunction resolveAssocCallTargetCand(ImplItemNode i) {
|
||||
NonMethodFunction resolveCallTargetNonBlanketCand(ImplItemNode i) {
|
||||
not this.hasTrait() and
|
||||
result = this.getPathResolutionResolved() and
|
||||
result = i.getASuccessor(_)
|
||||
or
|
||||
result = this.resolveCallTargetBlanketCand(i)
|
||||
result = i.getASuccessor(_) and
|
||||
FunctionOverloading::functionResolutionDependsOnArgument(_, result, _, _, _)
|
||||
}
|
||||
|
||||
AstNode getNodeAt(FunctionPosition pos) {
|
||||
@@ -2798,6 +2802,21 @@ private module NonMethodResolution {
|
||||
trait = this.getTrait()
|
||||
}
|
||||
|
||||
/**
|
||||
* Holds if this call has no compatible non-blanket target, and it has some
|
||||
* candidate blanket target.
|
||||
*/
|
||||
pragma[nomagic]
|
||||
predicate hasNoCompatibleNonBlanketTarget() {
|
||||
this.resolveCallTargetBlanketLikeCandidate(_, _, _, _) and
|
||||
not exists(this.resolveCallTargetViaPathResolution()) and
|
||||
forall(ImplOrTraitItemNode i, Function f |
|
||||
this.(NonMethodArgsAreInstantiationsOfNonBlanketInput::Call).hasTargetCand(i, f)
|
||||
|
|
||||
NonMethodArgsAreInstantiationsOfNonBlanket::argsAreNotInstantiationsOf(this, i, f)
|
||||
)
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the target of this call, which can be resolved using only path resolution.
|
||||
*/
|
||||
@@ -2816,7 +2835,9 @@ private module NonMethodResolution {
|
||||
result = this.resolveCallTargetBlanketCand(i) and
|
||||
not FunctionOverloading::functionResolutionDependsOnArgument(_, result, _, _, _)
|
||||
or
|
||||
NonMethodArgsAreInstantiationsOf::argsAreInstantiationsOf(this, i, result)
|
||||
NonMethodArgsAreInstantiationsOfBlanket::argsAreInstantiationsOf(this, i, result)
|
||||
or
|
||||
NonMethodArgsAreInstantiationsOfNonBlanket::argsAreInstantiationsOf(this, i, result)
|
||||
}
|
||||
|
||||
pragma[nomagic]
|
||||
@@ -2855,7 +2876,12 @@ private module NonMethodResolution {
|
||||
) {
|
||||
exists(NonMethodCall fc, FunctionPosition pos |
|
||||
fcp = MkCallAndBlanketPos(fc, pos) and
|
||||
fc.resolveCallTargetBlanketLikeCandidate(impl, pos, blanketPath, blanketTypeParam)
|
||||
fc.resolveCallTargetBlanketLikeCandidate(impl, pos, blanketPath, blanketTypeParam) and
|
||||
// Only apply blanket implementations when no other implementations are possible;
|
||||
// this is to account for codebases that use the (unstable) specialization feature
|
||||
// (https://rust-lang.github.io/rfcs/1210-impl-specialization.html), as well as
|
||||
// cases where our blanket implementation filtering is not precise enough.
|
||||
(fc.hasNoCompatibleNonBlanketTarget() or not impl.isBlanketImplementation())
|
||||
)
|
||||
}
|
||||
}
|
||||
@@ -2890,37 +2916,24 @@ private module NonMethodResolution {
|
||||
private module ArgIsInstantiationOfBlanketParam =
|
||||
ArgIsInstantiationOf<CallAndBlanketPos, ArgIsInstantiationOfBlanketParamInput>;
|
||||
|
||||
private module NonMethodArgsAreInstantiationsOfInput implements ArgsAreInstantiationsOfInputSig {
|
||||
private module NonMethodArgsAreInstantiationsOfBlanketInput implements
|
||||
ArgsAreInstantiationsOfInputSig
|
||||
{
|
||||
predicate toCheck(ImplOrTraitItemNode i, Function f, FunctionPosition pos, AssocFunctionType t) {
|
||||
t.appliesTo(f, i, pos) and
|
||||
(
|
||||
exists(Type t0 |
|
||||
// for now, we do not handle ambiguous targets when one of the types it iself
|
||||
// a type parameter; we should be checking the constraints on that type parameter
|
||||
// in this case
|
||||
not t0 instanceof TypeParameter
|
||||
|
|
||||
FunctionOverloading::functionResolutionDependsOnArgument(i, f, pos, _, t0)
|
||||
or
|
||||
traitFunctionDependsOnPos(_, _, pos, t0, i, f)
|
||||
)
|
||||
exists(Type t0 | typeCanBeUsedForDisambiguation(t0) |
|
||||
FunctionOverloading::functionResolutionDependsOnArgument(i, f, pos, _, t0)
|
||||
or
|
||||
// match against the trait function itself
|
||||
exists(Trait trait |
|
||||
FunctionOverloading::traitTypeParameterOccurrence(trait, f, _, pos, _,
|
||||
TSelfTypeParameter(trait))
|
||||
)
|
||||
traitFunctionDependsOnPos(_, _, pos, t0, i, f)
|
||||
)
|
||||
}
|
||||
|
||||
class Call extends NonMethodCall {
|
||||
final class Call extends NonMethodCall {
|
||||
Type getArgType(FunctionPosition pos, TypePath path) {
|
||||
result = inferType(this.getNodeAt(pos), path)
|
||||
}
|
||||
|
||||
predicate hasTargetCand(ImplOrTraitItemNode i, Function f) {
|
||||
f = this.resolveAssocCallTargetCand(i)
|
||||
or
|
||||
predicate hasTraitResolvedCand(ImplOrTraitItemNode i, Function f) {
|
||||
exists(TraitItemNode trait, NonMethodFunction resolved, ImplItemNode i1, Function f1 |
|
||||
this.hasTraitResolved(trait, resolved) and
|
||||
traitFunctionDependsOnPos(trait, resolved, _, _, i1, f1)
|
||||
@@ -2932,11 +2945,45 @@ private module NonMethodResolution {
|
||||
i = trait
|
||||
)
|
||||
}
|
||||
|
||||
predicate hasTargetCand(ImplOrTraitItemNode i, Function f) {
|
||||
f = this.resolveCallTargetBlanketCand(i)
|
||||
or
|
||||
this.hasTraitResolvedCand(i, f) and
|
||||
BlanketImplementation::isBlanketLike(i, _, _)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private module NonMethodArgsAreInstantiationsOf =
|
||||
ArgsAreInstantiationsOf<NonMethodArgsAreInstantiationsOfInput>;
|
||||
private module NonMethodArgsAreInstantiationsOfBlanket =
|
||||
ArgsAreInstantiationsOf<NonMethodArgsAreInstantiationsOfBlanketInput>;
|
||||
|
||||
private module NonMethodArgsAreInstantiationsOfNonBlanketInput implements
|
||||
ArgsAreInstantiationsOfInputSig
|
||||
{
|
||||
predicate toCheck(ImplOrTraitItemNode i, Function f, FunctionPosition pos, AssocFunctionType t) {
|
||||
NonMethodArgsAreInstantiationsOfBlanketInput::toCheck(i, f, pos, t)
|
||||
or
|
||||
// match against the trait function itself
|
||||
t.appliesTo(f, i, pos) and
|
||||
exists(Trait trait |
|
||||
FunctionOverloading::traitTypeParameterOccurrence(trait, f, _, pos, _,
|
||||
TSelfTypeParameter(trait))
|
||||
)
|
||||
}
|
||||
|
||||
class Call extends NonMethodArgsAreInstantiationsOfBlanketInput::Call {
|
||||
predicate hasTargetCand(ImplOrTraitItemNode i, Function f) {
|
||||
f = this.resolveCallTargetNonBlanketCand(i)
|
||||
or
|
||||
this.hasTraitResolvedCand(i, f) and
|
||||
not BlanketImplementation::isBlanketLike(i, _, _)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private module NonMethodArgsAreInstantiationsOfNonBlanket =
|
||||
ArgsAreInstantiationsOf<NonMethodArgsAreInstantiationsOfNonBlanketInput>;
|
||||
}
|
||||
|
||||
abstract private class TupleLikeConstructor extends Addressable {
|
||||
|
||||
@@ -2,22 +2,24 @@ models
|
||||
| 1 | Summary: <& as core::ops::deref::Deref>::deref; Argument[self].Reference; ReturnValue; value |
|
||||
| 2 | Summary: <_ as alloc::string::ToString>::to_string; Argument[self].Reference; ReturnValue; taint |
|
||||
| 3 | Summary: <_ as core::convert::From>::from; Argument[0]; ReturnValue; taint |
|
||||
| 4 | Summary: <_ as core::ops::deref::Deref>::deref; Argument[self].Reference; ReturnValue.Reference; taint |
|
||||
| 5 | Summary: <_ as core::ops::index::Index>::index; Argument[self].Reference.Element; ReturnValue.Reference; value |
|
||||
| 6 | Summary: <alloc::boxed::Box as core::ops::deref::Deref>::deref; Argument[self].Reference.Field[alloc::boxed::Box(0)]; ReturnValue.Reference; value |
|
||||
| 7 | Summary: <alloc::boxed::Box>::new; Argument[0]; ReturnValue.Field[alloc::boxed::Box(0)]; value |
|
||||
| 8 | Summary: <alloc::string::String as core::ops::deref::Deref>::deref; Argument[self]; ReturnValue; value |
|
||||
| 9 | Summary: <core::i64 as core::convert::From>::from; Argument[0]; ReturnValue; taint |
|
||||
| 10 | Summary: <core::option::Option>::unwrap; Argument[self].Field[core::option::Option::Some(0)]; ReturnValue; value |
|
||||
| 11 | Summary: <core::option::Option>::unwrap_or; Argument[0]; ReturnValue; value |
|
||||
| 12 | Summary: <core::option::Option>::unwrap_or; Argument[self].Field[core::option::Option::Some(0)]; ReturnValue; value |
|
||||
| 13 | Summary: <core::option::Option>::unwrap_or_else; Argument[0].ReturnValue; ReturnValue; value |
|
||||
| 14 | Summary: <core::option::Option>::unwrap_or_else; Argument[self].Field[core::option::Option::Some(0)]; ReturnValue; value |
|
||||
| 15 | Summary: <core::result::Result>::err; Argument[self].Field[core::result::Result::Err(0)]; ReturnValue.Field[core::option::Option::Some(0)]; value |
|
||||
| 16 | Summary: <core::result::Result>::expect; Argument[self].Field[core::result::Result::Ok(0)]; ReturnValue; value |
|
||||
| 17 | Summary: <core::result::Result>::expect_err; Argument[self].Field[core::result::Result::Err(0)]; ReturnValue; value |
|
||||
| 18 | Summary: <core::result::Result>::ok; Argument[self].Field[core::result::Result::Ok(0)]; ReturnValue.Field[core::option::Option::Some(0)]; value |
|
||||
| 19 | Summary: <core::result::Result>::unwrap; Argument[self].Field[core::result::Result::Ok(0)]; ReturnValue; value |
|
||||
| 4 | Summary: <_ as core::convert::Into>::into; Argument[self].Element; ReturnValue.Element; taint |
|
||||
| 5 | Summary: <_ as core::convert::Into>::into; Argument[self].Reference.Element; ReturnValue.Element; taint |
|
||||
| 6 | Summary: <_ as core::ops::deref::Deref>::deref; Argument[self].Reference; ReturnValue.Reference; taint |
|
||||
| 7 | Summary: <_ as core::ops::index::Index>::index; Argument[self].Reference.Element; ReturnValue.Reference; value |
|
||||
| 8 | Summary: <alloc::boxed::Box as core::ops::deref::Deref>::deref; Argument[self].Reference.Field[alloc::boxed::Box(0)]; ReturnValue.Reference; value |
|
||||
| 9 | Summary: <alloc::boxed::Box>::new; Argument[0]; ReturnValue.Field[alloc::boxed::Box(0)]; value |
|
||||
| 10 | Summary: <alloc::string::String as core::ops::deref::Deref>::deref; Argument[self]; ReturnValue; value |
|
||||
| 11 | Summary: <core::i64 as core::convert::From>::from; Argument[0]; ReturnValue; taint |
|
||||
| 12 | Summary: <core::option::Option>::unwrap; Argument[self].Field[core::option::Option::Some(0)]; ReturnValue; value |
|
||||
| 13 | Summary: <core::option::Option>::unwrap_or; Argument[0]; ReturnValue; value |
|
||||
| 14 | Summary: <core::option::Option>::unwrap_or; Argument[self].Field[core::option::Option::Some(0)]; ReturnValue; value |
|
||||
| 15 | Summary: <core::option::Option>::unwrap_or_else; Argument[0].ReturnValue; ReturnValue; value |
|
||||
| 16 | Summary: <core::option::Option>::unwrap_or_else; Argument[self].Field[core::option::Option::Some(0)]; ReturnValue; value |
|
||||
| 17 | Summary: <core::result::Result>::err; Argument[self].Field[core::result::Result::Err(0)]; ReturnValue.Field[core::option::Option::Some(0)]; value |
|
||||
| 18 | Summary: <core::result::Result>::expect; Argument[self].Field[core::result::Result::Ok(0)]; ReturnValue; value |
|
||||
| 19 | Summary: <core::result::Result>::expect_err; Argument[self].Field[core::result::Result::Err(0)]; ReturnValue; value |
|
||||
| 20 | Summary: <core::result::Result>::ok; Argument[self].Field[core::result::Result::Ok(0)]; ReturnValue.Field[core::option::Option::Some(0)]; value |
|
||||
| 21 | Summary: <core::result::Result>::unwrap; Argument[self].Field[core::result::Result::Ok(0)]; ReturnValue; value |
|
||||
edges
|
||||
| main.rs:23:9:23:9 | s | main.rs:24:10:24:10 | s | provenance | |
|
||||
| main.rs:23:9:23:9 | s | main.rs:26:12:26:12 | x | provenance | |
|
||||
@@ -45,8 +47,8 @@ edges
|
||||
| main.rs:82:5:82:5 | l | main.rs:83:10:83:10 | l | provenance | |
|
||||
| main.rs:115:9:115:9 | i [Box(0)] | main.rs:116:11:116:11 | i [Box(0)] | provenance | |
|
||||
| main.rs:115:13:115:31 | ...::new(...) [Box(0)] | main.rs:115:9:115:9 | i [Box(0)] | provenance | |
|
||||
| main.rs:115:22:115:30 | source(...) | main.rs:115:13:115:31 | ...::new(...) [Box(0)] | provenance | MaD:7 |
|
||||
| main.rs:116:11:116:11 | i [Box(0)] | main.rs:116:10:116:11 | * ... | provenance | MaD:6 |
|
||||
| main.rs:115:22:115:30 | source(...) | main.rs:115:13:115:31 | ...::new(...) [Box(0)] | provenance | MaD:9 |
|
||||
| main.rs:116:11:116:11 | i [Box(0)] | main.rs:116:10:116:11 | * ... | provenance | MaD:8 |
|
||||
| main.rs:123:9:123:9 | a [tuple.0] | main.rs:124:10:124:10 | a [tuple.0] | provenance | |
|
||||
| main.rs:123:13:123:26 | TupleExpr [tuple.0] | main.rs:123:9:123:9 | a [tuple.0] | provenance | |
|
||||
| main.rs:123:14:123:22 | source(...) | main.rs:123:13:123:26 | TupleExpr [tuple.0] | provenance | |
|
||||
@@ -129,17 +131,17 @@ edges
|
||||
| main.rs:278:9:278:10 | s1 [Some] | main.rs:279:10:279:11 | s1 [Some] | provenance | |
|
||||
| main.rs:278:14:278:29 | Some(...) [Some] | main.rs:278:9:278:10 | s1 [Some] | provenance | |
|
||||
| main.rs:278:19:278:28 | source(...) | main.rs:278:14:278:29 | Some(...) [Some] | provenance | |
|
||||
| main.rs:279:10:279:11 | s1 [Some] | main.rs:279:10:279:20 | s1.unwrap() | provenance | MaD:10 |
|
||||
| main.rs:279:10:279:11 | s1 [Some] | main.rs:279:10:279:20 | s1.unwrap() | provenance | MaD:12 |
|
||||
| main.rs:283:9:283:10 | s1 [Some] | main.rs:284:10:284:11 | s1 [Some] | provenance | |
|
||||
| main.rs:283:14:283:29 | Some(...) [Some] | main.rs:283:9:283:10 | s1 [Some] | provenance | |
|
||||
| main.rs:283:19:283:28 | source(...) | main.rs:283:14:283:29 | Some(...) [Some] | provenance | |
|
||||
| main.rs:284:10:284:11 | s1 [Some] | main.rs:284:10:284:24 | s1.unwrap_or(...) | provenance | MaD:12 |
|
||||
| main.rs:287:23:287:32 | source(...) | main.rs:287:10:287:33 | s2.unwrap_or(...) | provenance | MaD:11 |
|
||||
| main.rs:284:10:284:11 | s1 [Some] | main.rs:284:10:284:24 | s1.unwrap_or(...) | provenance | MaD:14 |
|
||||
| main.rs:287:23:287:32 | source(...) | main.rs:287:10:287:33 | s2.unwrap_or(...) | provenance | MaD:13 |
|
||||
| main.rs:291:9:291:10 | s1 [Some] | main.rs:292:10:292:11 | s1 [Some] | provenance | |
|
||||
| main.rs:291:14:291:29 | Some(...) [Some] | main.rs:291:9:291:10 | s1 [Some] | provenance | |
|
||||
| main.rs:291:19:291:28 | source(...) | main.rs:291:14:291:29 | Some(...) [Some] | provenance | |
|
||||
| main.rs:292:10:292:11 | s1 [Some] | main.rs:292:10:292:32 | s1.unwrap_or_else(...) | provenance | MaD:14 |
|
||||
| main.rs:295:31:295:40 | source(...) | main.rs:295:10:295:41 | s2.unwrap_or_else(...) | provenance | MaD:13 |
|
||||
| main.rs:292:10:292:11 | s1 [Some] | main.rs:292:10:292:32 | s1.unwrap_or_else(...) | provenance | MaD:16 |
|
||||
| main.rs:295:31:295:40 | source(...) | main.rs:295:10:295:41 | s2.unwrap_or_else(...) | provenance | MaD:15 |
|
||||
| main.rs:299:9:299:10 | s1 [Some] | main.rs:301:14:301:15 | s1 [Some] | provenance | |
|
||||
| main.rs:299:14:299:29 | Some(...) [Some] | main.rs:299:9:299:10 | s1 [Some] | provenance | |
|
||||
| main.rs:299:19:299:28 | source(...) | main.rs:299:14:299:29 | Some(...) [Some] | provenance | |
|
||||
@@ -150,16 +152,16 @@ edges
|
||||
| main.rs:308:32:308:45 | Ok(...) [Ok] | main.rs:308:9:308:10 | r1 [Ok] | provenance | |
|
||||
| main.rs:308:35:308:44 | source(...) | main.rs:308:32:308:45 | Ok(...) [Ok] | provenance | |
|
||||
| main.rs:309:9:309:11 | o1a [Some] | main.rs:311:10:311:12 | o1a [Some] | provenance | |
|
||||
| main.rs:309:28:309:29 | r1 [Ok] | main.rs:309:28:309:34 | r1.ok() [Some] | provenance | MaD:18 |
|
||||
| main.rs:309:28:309:29 | r1 [Ok] | main.rs:309:28:309:34 | r1.ok() [Some] | provenance | MaD:20 |
|
||||
| main.rs:309:28:309:34 | r1.ok() [Some] | main.rs:309:9:309:11 | o1a [Some] | provenance | |
|
||||
| main.rs:311:10:311:12 | o1a [Some] | main.rs:311:10:311:21 | o1a.unwrap() | provenance | MaD:10 |
|
||||
| main.rs:311:10:311:12 | o1a [Some] | main.rs:311:10:311:21 | o1a.unwrap() | provenance | MaD:12 |
|
||||
| main.rs:314:9:314:10 | r2 [Err] | main.rs:316:28:316:29 | r2 [Err] | provenance | |
|
||||
| main.rs:314:32:314:46 | Err(...) [Err] | main.rs:314:9:314:10 | r2 [Err] | provenance | |
|
||||
| main.rs:314:36:314:45 | source(...) | main.rs:314:32:314:46 | Err(...) [Err] | provenance | |
|
||||
| main.rs:316:9:316:11 | o2b [Some] | main.rs:318:10:318:12 | o2b [Some] | provenance | |
|
||||
| main.rs:316:28:316:29 | r2 [Err] | main.rs:316:28:316:35 | r2.err() [Some] | provenance | MaD:15 |
|
||||
| main.rs:316:28:316:29 | r2 [Err] | main.rs:316:28:316:35 | r2.err() [Some] | provenance | MaD:17 |
|
||||
| main.rs:316:28:316:35 | r2.err() [Some] | main.rs:316:9:316:11 | o2b [Some] | provenance | |
|
||||
| main.rs:318:10:318:12 | o2b [Some] | main.rs:318:10:318:21 | o2b.unwrap() | provenance | MaD:10 |
|
||||
| main.rs:318:10:318:12 | o2b [Some] | main.rs:318:10:318:21 | o2b.unwrap() | provenance | MaD:12 |
|
||||
| main.rs:322:9:322:10 | s1 [Ok] | main.rs:325:14:325:15 | s1 [Ok] | provenance | |
|
||||
| main.rs:322:32:322:45 | Ok(...) [Ok] | main.rs:322:9:322:10 | s1 [Ok] | provenance | |
|
||||
| main.rs:322:35:322:44 | source(...) | main.rs:322:32:322:45 | Ok(...) [Ok] | provenance | |
|
||||
@@ -169,11 +171,11 @@ edges
|
||||
| main.rs:335:9:335:10 | s1 [Ok] | main.rs:336:10:336:11 | s1 [Ok] | provenance | |
|
||||
| main.rs:335:32:335:45 | Ok(...) [Ok] | main.rs:335:9:335:10 | s1 [Ok] | provenance | |
|
||||
| main.rs:335:35:335:44 | source(...) | main.rs:335:32:335:45 | Ok(...) [Ok] | provenance | |
|
||||
| main.rs:336:10:336:11 | s1 [Ok] | main.rs:336:10:336:22 | s1.expect(...) | provenance | MaD:16 |
|
||||
| main.rs:336:10:336:11 | s1 [Ok] | main.rs:336:10:336:22 | s1.expect(...) | provenance | MaD:18 |
|
||||
| main.rs:339:9:339:10 | s2 [Err] | main.rs:341:10:341:11 | s2 [Err] | provenance | |
|
||||
| main.rs:339:32:339:46 | Err(...) [Err] | main.rs:339:9:339:10 | s2 [Err] | provenance | |
|
||||
| main.rs:339:36:339:45 | source(...) | main.rs:339:32:339:46 | Err(...) [Err] | provenance | |
|
||||
| main.rs:341:10:341:11 | s2 [Err] | main.rs:341:10:341:26 | s2.expect_err(...) | provenance | MaD:17 |
|
||||
| main.rs:341:10:341:11 | s2 [Err] | main.rs:341:10:341:26 | s2.expect_err(...) | provenance | MaD:19 |
|
||||
| main.rs:350:9:350:10 | s1 [A] | main.rs:352:11:352:12 | s1 [A] | provenance | |
|
||||
| main.rs:350:14:350:39 | ...::A(...) [A] | main.rs:350:9:350:10 | s1 [A] | provenance | |
|
||||
| main.rs:350:29:350:38 | source(...) | main.rs:350:14:350:39 | ...::A(...) [A] | provenance | |
|
||||
@@ -222,13 +224,13 @@ edges
|
||||
| main.rs:430:16:430:33 | [...] [element] | main.rs:430:9:430:12 | arr1 [element] | provenance | |
|
||||
| main.rs:430:23:430:32 | source(...) | main.rs:430:16:430:33 | [...] [element] | provenance | |
|
||||
| main.rs:431:9:431:10 | n1 | main.rs:432:10:432:11 | n1 | provenance | |
|
||||
| main.rs:431:14:431:17 | arr1 [element] | main.rs:431:14:431:20 | arr1[2] | provenance | MaD:5 |
|
||||
| main.rs:431:14:431:17 | arr1 [element] | main.rs:431:14:431:20 | arr1[2] | provenance | MaD:7 |
|
||||
| main.rs:431:14:431:20 | arr1[2] | main.rs:431:9:431:10 | n1 | provenance | |
|
||||
| main.rs:434:9:434:12 | arr2 [element] | main.rs:435:14:435:17 | arr2 [element] | provenance | |
|
||||
| main.rs:434:16:434:31 | [...; 10] [element] | main.rs:434:9:434:12 | arr2 [element] | provenance | |
|
||||
| main.rs:434:17:434:26 | source(...) | main.rs:434:16:434:31 | [...; 10] [element] | provenance | |
|
||||
| main.rs:435:9:435:10 | n2 | main.rs:436:10:436:11 | n2 | provenance | |
|
||||
| main.rs:435:14:435:17 | arr2 [element] | main.rs:435:14:435:20 | arr2[4] | provenance | MaD:5 |
|
||||
| main.rs:435:14:435:17 | arr2 [element] | main.rs:435:14:435:20 | arr2[4] | provenance | MaD:7 |
|
||||
| main.rs:435:14:435:20 | arr2[4] | main.rs:435:9:435:10 | n2 | provenance | |
|
||||
| main.rs:444:9:444:12 | arr1 [element] | main.rs:445:15:445:18 | arr1 [element] | provenance | |
|
||||
| main.rs:444:16:444:33 | [...] [element] | main.rs:444:9:444:12 | arr1 [element] | provenance | |
|
||||
@@ -249,9 +251,9 @@ edges
|
||||
| main.rs:470:5:470:11 | [post] mut_arr [element] | main.rs:473:10:473:16 | mut_arr [element] | provenance | |
|
||||
| main.rs:470:18:470:27 | source(...) | main.rs:470:5:470:11 | [post] mut_arr [element] | provenance | |
|
||||
| main.rs:471:9:471:9 | d | main.rs:472:10:472:10 | d | provenance | |
|
||||
| main.rs:471:13:471:19 | mut_arr [element] | main.rs:471:13:471:22 | mut_arr[1] | provenance | MaD:5 |
|
||||
| main.rs:471:13:471:19 | mut_arr [element] | main.rs:471:13:471:22 | mut_arr[1] | provenance | MaD:7 |
|
||||
| main.rs:471:13:471:22 | mut_arr[1] | main.rs:471:9:471:9 | d | provenance | |
|
||||
| main.rs:473:10:473:16 | mut_arr [element] | main.rs:473:10:473:19 | mut_arr[0] | provenance | MaD:5 |
|
||||
| main.rs:473:10:473:16 | mut_arr [element] | main.rs:473:10:473:19 | mut_arr[0] | provenance | MaD:7 |
|
||||
| main.rs:496:9:496:9 | s | main.rs:497:10:497:10 | s | provenance | |
|
||||
| main.rs:496:25:496:26 | source(...) | main.rs:496:9:496:9 | s | provenance | |
|
||||
| main.rs:505:9:505:9 | a | main.rs:506:13:506:13 | a | provenance | |
|
||||
@@ -263,26 +265,26 @@ edges
|
||||
| main.rs:506:13:506:13 | a | main.rs:506:13:506:25 | a.to_string() | provenance | MaD:2 |
|
||||
| main.rs:506:13:506:25 | a.to_string() | main.rs:506:9:506:9 | b | provenance | |
|
||||
| main.rs:507:9:507:9 | c | main.rs:512:10:512:10 | c | provenance | |
|
||||
| main.rs:507:13:507:13 | b | main.rs:507:13:507:28 | b.parse() [Ok] | provenance | MaD:4 |
|
||||
| main.rs:507:13:507:13 | b | main.rs:507:13:507:28 | b.parse() [Ok] | provenance | MaD:8 |
|
||||
| main.rs:507:13:507:28 | b.parse() [Ok] | main.rs:507:13:507:37 | ... .unwrap() | provenance | MaD:19 |
|
||||
| main.rs:507:13:507:13 | b | main.rs:507:13:507:28 | b.parse() [Ok] | provenance | MaD:6 |
|
||||
| main.rs:507:13:507:13 | b | main.rs:507:13:507:28 | b.parse() [Ok] | provenance | MaD:10 |
|
||||
| main.rs:507:13:507:28 | b.parse() [Ok] | main.rs:507:13:507:37 | ... .unwrap() | provenance | MaD:21 |
|
||||
| main.rs:507:13:507:37 | ... .unwrap() | main.rs:507:9:507:9 | c | provenance | |
|
||||
| main.rs:508:9:508:9 | d | main.rs:513:10:513:10 | d | provenance | |
|
||||
| main.rs:508:18:508:18 | b | main.rs:508:18:508:26 | b.parse() [Ok] | provenance | MaD:4 |
|
||||
| main.rs:508:18:508:18 | b | main.rs:508:18:508:26 | b.parse() [Ok] | provenance | MaD:8 |
|
||||
| main.rs:508:18:508:26 | b.parse() [Ok] | main.rs:508:18:508:35 | ... .unwrap() | provenance | MaD:19 |
|
||||
| main.rs:508:18:508:18 | b | main.rs:508:18:508:26 | b.parse() [Ok] | provenance | MaD:6 |
|
||||
| main.rs:508:18:508:18 | b | main.rs:508:18:508:26 | b.parse() [Ok] | provenance | MaD:10 |
|
||||
| main.rs:508:18:508:26 | b.parse() [Ok] | main.rs:508:18:508:35 | ... .unwrap() | provenance | MaD:21 |
|
||||
| main.rs:508:18:508:35 | ... .unwrap() | main.rs:508:9:508:9 | d | provenance | |
|
||||
| main.rs:517:9:517:10 | vs [element] | main.rs:519:10:519:11 | vs [element] | provenance | |
|
||||
| main.rs:517:9:517:10 | vs [element] | main.rs:523:14:523:15 | vs [element] | provenance | |
|
||||
| main.rs:517:14:517:34 | [...] [element] | main.rs:517:9:517:10 | vs [element] | provenance | |
|
||||
| main.rs:517:15:517:24 | source(...) | main.rs:517:14:517:34 | [...] [element] | provenance | |
|
||||
| main.rs:519:10:519:11 | vs [element] | main.rs:519:10:519:14 | vs[0] | provenance | MaD:5 |
|
||||
| main.rs:519:10:519:11 | vs [element] | main.rs:519:10:519:14 | vs[0] | provenance | MaD:7 |
|
||||
| main.rs:523:9:523:9 | v | main.rs:524:14:524:14 | v | provenance | |
|
||||
| main.rs:523:14:523:15 | vs [element] | main.rs:523:9:523:9 | v | provenance | |
|
||||
| main.rs:542:9:542:18 | mut vs_mut [element] | main.rs:544:10:544:15 | vs_mut [element] | provenance | |
|
||||
| main.rs:542:22:542:42 | [...] [element] | main.rs:542:9:542:18 | mut vs_mut [element] | provenance | |
|
||||
| main.rs:542:23:542:32 | source(...) | main.rs:542:22:542:42 | [...] [element] | provenance | |
|
||||
| main.rs:544:10:544:15 | vs_mut [element] | main.rs:544:10:544:18 | vs_mut[0] | provenance | MaD:5 |
|
||||
| main.rs:544:10:544:15 | vs_mut [element] | main.rs:544:10:544:18 | vs_mut[0] | provenance | MaD:7 |
|
||||
| main.rs:554:9:554:9 | a | main.rs:559:10:559:10 | a | provenance | |
|
||||
| main.rs:554:13:554:22 | source(...) | main.rs:554:9:554:9 | a | provenance | |
|
||||
| main.rs:555:9:555:9 | b | main.rs:560:15:560:15 | b | provenance | |
|
||||
@@ -296,12 +298,20 @@ edges
|
||||
| main.rs:560:15:560:15 | b | main.rs:560:14:560:15 | &b | provenance | |
|
||||
| main.rs:562:11:562:15 | c_ref [&ref] | main.rs:562:10:562:15 | * ... | provenance | MaD:1 |
|
||||
| main.rs:566:9:566:9 | a | main.rs:568:10:568:17 | a as i64 | provenance | |
|
||||
| main.rs:566:9:566:9 | a | main.rs:569:10:569:10 | a | provenance | |
|
||||
| main.rs:566:9:566:9 | a | main.rs:570:20:570:20 | a | provenance | |
|
||||
| main.rs:566:18:566:27 | source(...) | main.rs:566:9:566:9 | a | provenance | |
|
||||
| main.rs:569:10:569:10 | a | main.rs:569:10:569:17 | a.into() | provenance | MaD:4 |
|
||||
| main.rs:569:10:569:10 | a | main.rs:569:10:569:17 | a.into() | provenance | MaD:5 |
|
||||
| main.rs:570:20:570:20 | a | main.rs:570:10:570:21 | ...::from(...) | provenance | ReflexiveFrom |
|
||||
| main.rs:572:9:572:9 | b | main.rs:574:10:574:17 | b as i64 | provenance | |
|
||||
| main.rs:572:9:572:9 | b | main.rs:575:10:575:10 | b | provenance | |
|
||||
| main.rs:572:9:572:9 | b | main.rs:576:20:576:20 | b | provenance | |
|
||||
| main.rs:572:18:572:27 | source(...) | main.rs:572:9:572:9 | b | provenance | |
|
||||
| main.rs:575:10:575:10 | b | main.rs:575:10:575:17 | b.into() | provenance | MaD:4 |
|
||||
| main.rs:575:10:575:10 | b | main.rs:575:10:575:17 | b.into() | provenance | MaD:5 |
|
||||
| main.rs:576:20:576:20 | b | main.rs:576:10:576:21 | ...::from(...) | provenance | MaD:3 |
|
||||
| main.rs:576:20:576:20 | b | main.rs:576:10:576:21 | ...::from(...) | provenance | MaD:9 |
|
||||
| main.rs:576:20:576:20 | b | main.rs:576:10:576:21 | ...::from(...) | provenance | MaD:11 |
|
||||
nodes
|
||||
| main.rs:19:10:19:18 | source(...) | semmle.label | source(...) |
|
||||
| main.rs:23:9:23:9 | s | semmle.label | s |
|
||||
@@ -630,9 +640,15 @@ nodes
|
||||
| main.rs:566:9:566:9 | a | semmle.label | a |
|
||||
| main.rs:566:18:566:27 | source(...) | semmle.label | source(...) |
|
||||
| main.rs:568:10:568:17 | a as i64 | semmle.label | a as i64 |
|
||||
| main.rs:569:10:569:10 | a | semmle.label | a |
|
||||
| main.rs:569:10:569:17 | a.into() | semmle.label | a.into() |
|
||||
| main.rs:570:10:570:21 | ...::from(...) | semmle.label | ...::from(...) |
|
||||
| main.rs:570:20:570:20 | a | semmle.label | a |
|
||||
| main.rs:572:9:572:9 | b | semmle.label | b |
|
||||
| main.rs:572:18:572:27 | source(...) | semmle.label | source(...) |
|
||||
| main.rs:574:10:574:17 | b as i64 | semmle.label | b as i64 |
|
||||
| main.rs:575:10:575:10 | b | semmle.label | b |
|
||||
| main.rs:575:10:575:17 | b.into() | semmle.label | b.into() |
|
||||
| main.rs:576:10:576:21 | ...::from(...) | semmle.label | ...::from(...) |
|
||||
| main.rs:576:20:576:20 | b | semmle.label | b |
|
||||
subpaths
|
||||
@@ -707,5 +723,8 @@ testFailures
|
||||
| main.rs:561:14:561:18 | c_ref | main.rs:556:13:556:22 | source(...) | main.rs:561:14:561:18 | c_ref | $@ | main.rs:556:13:556:22 | source(...) | source(...) |
|
||||
| main.rs:562:10:562:15 | * ... | main.rs:556:13:556:22 | source(...) | main.rs:562:10:562:15 | * ... | $@ | main.rs:556:13:556:22 | source(...) | source(...) |
|
||||
| main.rs:568:10:568:17 | a as i64 | main.rs:566:18:566:27 | source(...) | main.rs:568:10:568:17 | a as i64 | $@ | main.rs:566:18:566:27 | source(...) | source(...) |
|
||||
| main.rs:569:10:569:17 | a.into() | main.rs:566:18:566:27 | source(...) | main.rs:569:10:569:17 | a.into() | $@ | main.rs:566:18:566:27 | source(...) | source(...) |
|
||||
| main.rs:570:10:570:21 | ...::from(...) | main.rs:566:18:566:27 | source(...) | main.rs:570:10:570:21 | ...::from(...) | $@ | main.rs:566:18:566:27 | source(...) | source(...) |
|
||||
| main.rs:574:10:574:17 | b as i64 | main.rs:572:18:572:27 | source(...) | main.rs:574:10:574:17 | b as i64 | $@ | main.rs:572:18:572:27 | source(...) | source(...) |
|
||||
| main.rs:575:10:575:17 | b.into() | main.rs:572:18:572:27 | source(...) | main.rs:575:10:575:17 | b.into() | $@ | main.rs:572:18:572:27 | source(...) | source(...) |
|
||||
| main.rs:576:10:576:21 | ...::from(...) | main.rs:572:18:572:27 | source(...) | main.rs:576:10:576:21 | ...::from(...) | $@ | main.rs:572:18:572:27 | source(...) | source(...) |
|
||||
|
||||
@@ -566,13 +566,13 @@ fn conversions() {
|
||||
let a: i64 = source(50);
|
||||
|
||||
sink(a as i64); // $ hasTaintFlow=50
|
||||
sink(a.into()); // $ MISSING: hasValueFlow=50
|
||||
sink(i64::from(a)); // $ MISSING: hasTaintFlow=50 -- we cannot resolve the `impl<T> From<T> for T` implementation
|
||||
sink(a.into()); // $ SPURIOUS: hasTaintFlow=50 $ MISSING: hasValueFlow=50 -- it is not possible to define a value-preserving summary for `into` since it depends on which `from` function is called
|
||||
sink(i64::from(a)); // $ hasValueFlow=50
|
||||
|
||||
let b: i32 = source(51) as i32;
|
||||
|
||||
sink(b as i64); // $ hasTaintFlow=51
|
||||
sink(b.into()); // $ MISSING: hasTaintFlow=51
|
||||
sink(b.into()); // $ hasTaintFlow=51
|
||||
sink(i64::from(b)); // $ hasTaintFlow=51
|
||||
}
|
||||
|
||||
|
||||
@@ -2595,7 +2595,7 @@ mod tuples {
|
||||
let i: i64 = pair.0; // $ fieldof=Tuple2
|
||||
let j: bool = pair.1; // $ fieldof=Tuple2
|
||||
|
||||
let pair = [1, 1].into(); // $ type=pair:(T_2) type=pair:T0.i32 type=pair:T1.i32 MISSING: target=into
|
||||
let pair = [1, 1].into(); // $ type=pair:(T_2) type=pair:T0.i32 type=pair:T1.i32 target=into
|
||||
match pair {
|
||||
(0, 0) => print!("unexpected"),
|
||||
_ => print!("expected"),
|
||||
|
||||
Reference in New Issue
Block a user