Skip to content

Commit 1264cfa

Browse files
committed
[semantic-sil] Add a semantic attribute "verify.ownership.sil.never".
This semantic attribute allows a user to disable ownership verification on specific functions. The intention is that once I turn on the sil ownership verifier for parts of the stdlib, if an engineer exposes an ownership issue, they can disable ownership verification on that specific function, file a bug, and continue with their work. rdar://31880847
1 parent d84e4b4 commit 1264cfa

File tree

4 files changed

+48
-6
lines changed

4 files changed

+48
-6
lines changed

include/swift/SIL/SILFunction.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -456,6 +456,10 @@ class SILFunction
456456
/// or is raw SIL (so that the mandatory passes still run).
457457
bool shouldOptimize() const;
458458

459+
/// Returns true if this is a function that should have its ownership
460+
/// verified.
461+
bool shouldVerifyOwnership() const;
462+
459463
/// Check if the function has a location.
460464
/// FIXME: All functions should have locations, so this method should not be
461465
/// necessary.

lib/SIL/SILFunction.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -464,3 +464,7 @@ SubstitutionList SILFunction::getForwardingSubstitutions() {
464464
ForwardingSubs = env->getForwardingSubstitutions();
465465
return *ForwardingSubs;
466466
}
467+
468+
bool SILFunction::shouldVerifyOwnership() const {
469+
return !hasSemanticsAttr("verify.ownership.sil.never");
470+
}

lib/SIL/SILOwnershipVerifier.cpp

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2068,9 +2068,10 @@ void SILInstruction::verifyOperandOwnership() const {
20682068
if (!getModule().getOptions().EnableSILOwnership)
20692069
return;
20702070

2071-
// If the given function has unqualified ownership, there is nothing to
2072-
// verify.
2073-
if (getFunction()->hasUnqualifiedOwnership())
2071+
// If the given function has unqualified ownership or we have been asked by
2072+
// the user not to verify this function, there is nothing to verify.
2073+
if (getFunction()->hasUnqualifiedOwnership() ||
2074+
!getFunction()->shouldVerifyOwnership())
20742075
return;
20752076

20762077
// If we are testing the verifier, bail so we only print errors once when
@@ -2116,9 +2117,9 @@ void SILValue::verifyOwnership(SILModule &Mod,
21162117
SILFunction *F = (*this)->getFunction();
21172118
assert(F && "Instructions and arguments should have a function");
21182119

2119-
// If the given function has unqualified ownership, there is nothing further
2120-
// to verify.
2121-
if (F->hasUnqualifiedOwnership())
2120+
// If the given function has unqualified ownership or we have been asked by
2121+
// the user not to verify this function, there is nothing to verify.
2122+
if (F->hasUnqualifiedOwnership() || !F->shouldVerifyOwnership())
21222123
return;
21232124

21242125
ErrorBehaviorKind ErrorBehavior;
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
// RUN: %target-sil-opt -enable-sil-ownership -sil-ownership-verifier-enable-testing -enable-sil-verify-all=0 %s -o /dev/null 2>&1 | %FileCheck %s
2+
// REQUIRES: asserts
3+
4+
// This test makes sure that the ownership verifier can be disabled on specific
5+
// functions via the usage of the semantic attribute
6+
// "verify.ownership.sil.never".
7+
8+
sil_stage canonical
9+
10+
import Builtin
11+
12+
sil [_semantics "verify.ownership.sil.never"] @test1 : $@convention(thin) (@owned Builtin.NativeObject) -> () {
13+
bb0(%0 : @owned $Builtin.NativeObject):
14+
destroy_value %0 : $Builtin.NativeObject
15+
destroy_value %0 : $Builtin.NativeObject
16+
%9999 = tuple()
17+
return %9999 : $()
18+
}
19+
20+
// CHECK-NOT: Function: 'test1'
21+
// CHECK-LABEL: Function: 'test2'
22+
// CHECK-NEXT: Found over consume?!
23+
// CHECK-NEXT: Value: %0 = argument of bb0 : $Builtin.NativeObject
24+
// CHECK-NEXT: User: destroy_value %0 : $Builtin.NativeObject
25+
// CHECK-NEXT: Block: bb0
26+
// CHECK-NOT: Function: 'test1'
27+
sil @test2 : $@convention(thin) (@owned Builtin.NativeObject) -> () {
28+
bb0(%0 : @owned $Builtin.NativeObject):
29+
destroy_value %0 : $Builtin.NativeObject
30+
destroy_value %0 : $Builtin.NativeObject
31+
%9999 = tuple()
32+
return %9999 : $()
33+
}

0 commit comments

Comments
 (0)