C++: Model for smart pointer destructors

This commit is contained in:
Robert Marsh
2024-02-13 01:00:46 +00:00
parent b6cf64cff3
commit f791b0ebbf
4 changed files with 106 additions and 105 deletions

View File

@@ -168,3 +168,58 @@ private class SmartPtrSetterFunction extends MemberFunction, AliasFunction, Side
)
}
}
/** A destructor assocaited with a smart pointer. */
private class SmartPtrDestructor extends Destructor, SideEffectFunction, AliasFunction {
SmartPtr declaringType;
SmartPtrDestructor() {
declaringType = this.getDeclaringType() and not this.isFromUninstantiatedTemplate(_)
}
/**
* Gets the destructor associated with the base type of this smart pointer.
*/
private Destructor getBaseTypeDestructor() {
// TODO: Check if this is join ordered correctly.
result.getDeclaringType() = declaringType.getBaseType()
}
override predicate hasOnlySpecificReadSideEffects() {
this.getBaseTypeDestructor().(SideEffectFunction).hasOnlySpecificReadSideEffects()
or
// If there's no declared destructor for the base type then it won't have
// any strange read side effects.
not exists(this.getBaseTypeDestructor())
}
override predicate hasOnlySpecificWriteSideEffects() {
this.getBaseTypeDestructor().(SideEffectFunction).hasOnlySpecificWriteSideEffects()
or
// If there's no declared destructor for the base type then it won't have
// any strange write side effects.
not exists(this.getBaseTypeDestructor())
}
override predicate hasSpecificReadSideEffect(ParameterIndex i, boolean buffer) {
i = -1 and buffer = false
}
override predicate hasSpecificWriteSideEffect(ParameterIndex i, boolean buffer, boolean mustWrite) {
i = -1 and buffer = false and mustWrite = true
}
override predicate parameterNeverEscapes(int index) {
this.getBaseTypeDestructor().(AliasFunction).parameterNeverEscapes(index)
or
// If there's no declared destructor for the base type then it won't cause
// anything to escape.
not exists(this.getBaseTypeDestructor()) and
index = -1
}
override predicate parameterEscapesOnlyViaReturn(int index) {
// A destructor call does not have a return value
none()
}
}

View File

@@ -10952,13 +10952,13 @@
| perf-regression.cpp:12:10:12:10 | StoreValue | r12_2 |
| smart_ptr.cpp:10:6:10:24 | ChiPartial | partial:m10_3 |
| smart_ptr.cpp:10:6:10:24 | ChiTotal | total:m10_2 |
| smart_ptr.cpp:10:6:10:24 | SideEffect | ~m13_6 |
| smart_ptr.cpp:10:6:10:24 | SideEffect | ~m12_12 |
| smart_ptr.cpp:10:31:10:31 | Address | &:r10_5 |
| smart_ptr.cpp:10:31:10:31 | Address | &:r10_5 |
| smart_ptr.cpp:10:31:10:31 | Address | &:r10_7 |
| smart_ptr.cpp:10:31:10:31 | Address | &:r10_7 |
| smart_ptr.cpp:10:31:10:31 | Load | m10_6 |
| smart_ptr.cpp:10:31:10:31 | SideEffect | m10_8 |
| smart_ptr.cpp:10:31:10:31 | SideEffect | m12_15 |
| smart_ptr.cpp:11:21:11:22 | Address | &:r11_1 |
| smart_ptr.cpp:11:21:11:22 | Address | &:r11_1 |
| smart_ptr.cpp:11:21:11:22 | Arg(this) | this:r11_1 |
@@ -10981,9 +10981,9 @@
| smart_ptr.cpp:12:20:12:27 | Address | &:r12_9 |
| smart_ptr.cpp:12:20:12:27 | Arg(0) | 0:r12_9 |
| smart_ptr.cpp:12:20:12:27 | ChiPartial | partial:m12_14 |
| smart_ptr.cpp:12:20:12:27 | ChiTotal | total:m12_12 |
| smart_ptr.cpp:12:20:12:27 | ChiTotal | total:m10_8 |
| smart_ptr.cpp:12:20:12:27 | Load | m12_8 |
| smart_ptr.cpp:12:20:12:27 | SideEffect | ~m12_12 |
| smart_ptr.cpp:12:20:12:27 | SideEffect | ~m10_8 |
| smart_ptr.cpp:12:24:12:28 | Load | m11_9 |
| smart_ptr.cpp:12:24:12:28 | StoreValue | r12_7 |
| smart_ptr.cpp:12:25:12:26 | Arg(0) | 0:r12_5 |
@@ -10992,21 +10992,16 @@
| smart_ptr.cpp:13:1:13:1 | Address | &:r13_2 |
| smart_ptr.cpp:13:1:13:1 | Arg(this) | this:r13_2 |
| smart_ptr.cpp:13:1:13:1 | CallTarget | func:r13_3 |
| smart_ptr.cpp:13:1:13:1 | ChiPartial | partial:m13_5 |
| smart_ptr.cpp:13:1:13:1 | ChiPartial | partial:m13_8 |
| smart_ptr.cpp:13:1:13:1 | ChiTotal | total:m11_9 |
| smart_ptr.cpp:13:1:13:1 | ChiTotal | total:m12_15 |
| smart_ptr.cpp:13:1:13:1 | SideEffect | m11_9 |
| smart_ptr.cpp:13:1:13:1 | SideEffect | ~m12_15 |
| smart_ptr.cpp:17:6:17:24 | ChiPartial | partial:m17_3 |
| smart_ptr.cpp:17:6:17:24 | ChiTotal | total:m17_2 |
| smart_ptr.cpp:17:6:17:24 | SideEffect | ~m20_6 |
| smart_ptr.cpp:17:6:17:24 | SideEffect | ~m19_16 |
| smart_ptr.cpp:17:33:17:33 | Address | &:r17_5 |
| smart_ptr.cpp:17:33:17:33 | Address | &:r17_5 |
| smart_ptr.cpp:17:33:17:33 | Address | &:r17_7 |
| smart_ptr.cpp:17:33:17:33 | Address | &:r17_7 |
| smart_ptr.cpp:17:33:17:33 | Load | m17_6 |
| smart_ptr.cpp:17:33:17:33 | SideEffect | m17_8 |
| smart_ptr.cpp:17:33:17:33 | SideEffect | m19_19 |
| smart_ptr.cpp:18:23:18:24 | Address | &:r18_1 |
| smart_ptr.cpp:18:23:18:24 | Address | &:r18_1 |
| smart_ptr.cpp:18:23:18:24 | Arg(this) | this:r18_1 |
@@ -11033,27 +11028,22 @@
| smart_ptr.cpp:19:20:19:21 | CallTarget | func:r19_4 |
| smart_ptr.cpp:19:20:19:21 | ChiPartial | partial:m19_9 |
| smart_ptr.cpp:19:20:19:21 | ChiPartial | partial:m19_18 |
| smart_ptr.cpp:19:20:19:21 | ChiTotal | total:m17_8 |
| smart_ptr.cpp:19:20:19:21 | ChiTotal | total:m18_8 |
| smart_ptr.cpp:19:20:19:21 | ChiTotal | total:m19_16 |
| smart_ptr.cpp:19:20:19:21 | Load | m19_12 |
| smart_ptr.cpp:19:20:19:21 | SideEffect | m18_9 |
| smart_ptr.cpp:19:20:19:21 | SideEffect | ~m17_8 |
| smart_ptr.cpp:19:20:19:21 | SideEffect | ~m18_8 |
| smart_ptr.cpp:19:20:19:21 | SideEffect | ~m19_16 |
| smart_ptr.cpp:19:20:19:21 | Unary | r19_5 |
| smart_ptr.cpp:19:20:19:21 | Unary | r19_6 |
| smart_ptr.cpp:20:1:20:1 | Address | &:r20_2 |
| smart_ptr.cpp:20:1:20:1 | Address | &:r20_2 |
| smart_ptr.cpp:20:1:20:1 | Arg(this) | this:r20_2 |
| smart_ptr.cpp:20:1:20:1 | CallTarget | func:r20_3 |
| smart_ptr.cpp:20:1:20:1 | ChiPartial | partial:m20_5 |
| smart_ptr.cpp:20:1:20:1 | ChiPartial | partial:m20_8 |
| smart_ptr.cpp:20:1:20:1 | ChiTotal | total:m18_9 |
| smart_ptr.cpp:20:1:20:1 | ChiTotal | total:m19_19 |
| smart_ptr.cpp:20:1:20:1 | SideEffect | m18_9 |
| smart_ptr.cpp:20:1:20:1 | SideEffect | ~m19_19 |
| smart_ptr.cpp:28:6:28:27 | ChiPartial | partial:m28_3 |
| smart_ptr.cpp:28:6:28:27 | ChiTotal | total:m28_2 |
| smart_ptr.cpp:28:6:28:27 | SideEffect | ~m48_38 |
| smart_ptr.cpp:28:6:28:27 | SideEffect | ~m47_16 |
| smart_ptr.cpp:29:27:29:38 | Address | &:r29_1 |
| smart_ptr.cpp:31:5:31:24 | CallTarget | func:r31_1 |
| smart_ptr.cpp:31:5:31:24 | ChiPartial | partial:m31_15 |
@@ -11175,54 +11165,29 @@
| smart_ptr.cpp:47:43:47:63 | Unary | r47_6 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_2 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_2 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_10 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_10 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_18 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_18 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_26 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_26 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_34 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_34 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_7 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_7 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_12 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_12 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_17 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_17 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_22 |
| smart_ptr.cpp:48:1:48:1 | Address | &:r48_22 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_2 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_10 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_18 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_26 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_34 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_7 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_12 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_17 |
| smart_ptr.cpp:48:1:48:1 | Arg(this) | this:r48_22 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_3 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_11 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_19 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_27 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_35 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_5 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_8 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_13 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_16 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_21 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_24 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_29 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_32 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_37 |
| smart_ptr.cpp:48:1:48:1 | ChiPartial | partial:m48_40 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m29_2 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m33_2 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m37_2 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m41_2 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m45_2 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m47_16 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m48_6 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m48_14 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m48_22 |
| smart_ptr.cpp:48:1:48:1 | ChiTotal | total:m48_30 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_8 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_13 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_18 |
| smart_ptr.cpp:48:1:48:1 | CallTarget | func:r48_23 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | m29_2 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | m33_2 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | m37_2 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | m41_2 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | m45_2 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | ~m47_16 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | ~m48_6 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | ~m48_14 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | ~m48_22 |
| smart_ptr.cpp:48:1:48:1 | SideEffect | ~m48_30 |
| struct_init.cpp:9:13:9:25 | Left | r9_3 |
| struct_init.cpp:9:13:9:25 | Left | r9_3 |
| struct_init.cpp:9:13:9:25 | SideEffect | ~m11_10 |

View File

@@ -12469,9 +12469,8 @@ smart_ptr.cpp:
# 13| r13_2(glval<unique_ptr<int, default_delete<int>>>) = VariableAddress[up] :
# 13| r13_3(glval<unknown>) = FunctionAddress[~unique_ptr] :
# 13| v13_4(void) = Call[~unique_ptr] : func:r13_3, this:r13_2
# 13| mu13_5(unknown) = ^CallSideEffect : ~m?
# 13| v13_6(void) = ^IndirectReadSideEffect[-1] : &:r13_2, ~m?
# 13| mu13_7(unique_ptr<int, default_delete<int>>) = ^IndirectMayWriteSideEffect[-1] : &:r13_2
# 13| v13_5(void) = ^IndirectReadSideEffect[-1] : &:r13_2, ~m?
# 13| mu13_6(unique_ptr<int, default_delete<int>>) = ^IndirectMustWriteSideEffect[-1] : &:r13_2
# 10| v10_8(void) = ReturnIndirection[p] : &:r10_6, ~m?
# 10| v10_9(void) = ReturnVoid :
# 10| v10_10(void) = AliasedUse : ~m?
@@ -12514,9 +12513,8 @@ smart_ptr.cpp:
# 20| r20_2(glval<shared_ptr<float>>) = VariableAddress[sp] :
# 20| r20_3(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 20| v20_4(void) = Call[~shared_ptr] : func:r20_3, this:r20_2
# 20| mu20_5(unknown) = ^CallSideEffect : ~m?
# 20| v20_6(void) = ^IndirectReadSideEffect[-1] : &:r20_2, ~m?
# 20| mu20_7(shared_ptr<float>) = ^IndirectMayWriteSideEffect[-1] : &:r20_2
# 20| v20_5(void) = ^IndirectReadSideEffect[-1] : &:r20_2, ~m?
# 20| mu20_6(shared_ptr<float>) = ^IndirectMustWriteSideEffect[-1] : &:r20_2
# 17| v17_8(void) = ReturnIndirection[p] : &:r17_6, ~m?
# 17| v17_9(void) = ReturnVoid :
# 17| v17_10(void) = AliasedUse : ~m?
@@ -12619,33 +12617,28 @@ smart_ptr.cpp:
# 48| r48_2(glval<shared_ptr<const shared_ptr<const int>>>) = VariableAddress[sp_const_sp_const_int] :
# 48| r48_3(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_4(void) = Call[~shared_ptr] : func:r48_3, this:r48_2
# 48| mu48_5(unknown) = ^CallSideEffect : ~m?
# 48| v48_6(void) = ^IndirectReadSideEffect[-1] : &:r48_2, ~m?
# 48| mu48_7(shared_ptr<const shared_ptr<const int>>) = ^IndirectMayWriteSideEffect[-1] : &:r48_2
# 48| r48_8(glval<shared_ptr<const shared_ptr<int>>>) = VariableAddress[sp_const_sp_int] :
# 48| r48_9(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_10(void) = Call[~shared_ptr] : func:r48_9, this:r48_8
# 48| mu48_11(unknown) = ^CallSideEffect : ~m?
# 48| v48_12(void) = ^IndirectReadSideEffect[-1] : &:r48_8, ~m?
# 48| mu48_13(shared_ptr<const shared_ptr<int>>) = ^IndirectMayWriteSideEffect[-1] : &:r48_8
# 48| r48_14(glval<shared_ptr<shared_ptr<const int>>>) = VariableAddress[sp_sp_const_int] :
# 48| r48_15(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_16(void) = Call[~shared_ptr] : func:r48_15, this:r48_14
# 48| mu48_17(unknown) = ^CallSideEffect : ~m?
# 48| v48_18(void) = ^IndirectReadSideEffect[-1] : &:r48_14, ~m?
# 48| mu48_19(shared_ptr<shared_ptr<const int>>) = ^IndirectMayWriteSideEffect[-1] : &:r48_14
# 48| r48_20(glval<shared_ptr<int *const>>) = VariableAddress[sp_const_int_pointer] :
# 48| r48_21(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_22(void) = Call[~shared_ptr] : func:r48_21, this:r48_20
# 48| mu48_23(unknown) = ^CallSideEffect : ~m?
# 48| v48_24(void) = ^IndirectReadSideEffect[-1] : &:r48_20, ~m?
# 48| mu48_25(shared_ptr<int *const>) = ^IndirectMayWriteSideEffect[-1] : &:r48_20
# 48| r48_26(glval<shared_ptr<const int>>) = VariableAddress[sp_const_int] :
# 48| r48_27(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_28(void) = Call[~shared_ptr] : func:r48_27, this:r48_26
# 48| mu48_29(unknown) = ^CallSideEffect : ~m?
# 48| v48_30(void) = ^IndirectReadSideEffect[-1] : &:r48_26, ~m?
# 48| mu48_31(shared_ptr<const int>) = ^IndirectMayWriteSideEffect[-1] : &:r48_26
# 48| v48_5(void) = ^IndirectReadSideEffect[-1] : &:r48_2, ~m?
# 48| mu48_6(shared_ptr<const shared_ptr<const int>>) = ^IndirectMustWriteSideEffect[-1] : &:r48_2
# 48| r48_7(glval<shared_ptr<const shared_ptr<int>>>) = VariableAddress[sp_const_sp_int] :
# 48| r48_8(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_9(void) = Call[~shared_ptr] : func:r48_8, this:r48_7
# 48| v48_10(void) = ^IndirectReadSideEffect[-1] : &:r48_7, ~m?
# 48| mu48_11(shared_ptr<const shared_ptr<int>>) = ^IndirectMustWriteSideEffect[-1] : &:r48_7
# 48| r48_12(glval<shared_ptr<shared_ptr<const int>>>) = VariableAddress[sp_sp_const_int] :
# 48| r48_13(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_14(void) = Call[~shared_ptr] : func:r48_13, this:r48_12
# 48| v48_15(void) = ^IndirectReadSideEffect[-1] : &:r48_12, ~m?
# 48| mu48_16(shared_ptr<shared_ptr<const int>>) = ^IndirectMustWriteSideEffect[-1] : &:r48_12
# 48| r48_17(glval<shared_ptr<int *const>>) = VariableAddress[sp_const_int_pointer] :
# 48| r48_18(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_19(void) = Call[~shared_ptr] : func:r48_18, this:r48_17
# 48| v48_20(void) = ^IndirectReadSideEffect[-1] : &:r48_17, ~m?
# 48| mu48_21(shared_ptr<int *const>) = ^IndirectMustWriteSideEffect[-1] : &:r48_17
# 48| r48_22(glval<shared_ptr<const int>>) = VariableAddress[sp_const_int] :
# 48| r48_23(glval<unknown>) = FunctionAddress[~shared_ptr] :
# 48| v48_24(void) = Call[~shared_ptr] : func:r48_23, this:r48_22
# 48| v48_25(void) = ^IndirectReadSideEffect[-1] : &:r48_22, ~m?
# 48| mu48_26(shared_ptr<const int>) = ^IndirectMustWriteSideEffect[-1] : &:r48_22
# 28| v28_4(void) = ReturnVoid :
# 28| v28_5(void) = AliasedUse : ~m?
# 28| v28_6(void) = ExitFunction :

View File

@@ -1,14 +1,2 @@
testFailures
| smart_pointer.cpp:13:21:13:49 | //$ussa=dynamic{1}[0..4)<int> | Missing result:ussa=dynamic{1}[0..4)<int> |
| smart_pointer.cpp:14:14:14:40 | //$ussa=dynamic{1}[0..4)<S> | Missing result:ussa=dynamic{1}[0..4)<S> |
| smart_pointer.cpp:16:22:16:48 | //$ussa=dynamic{1}[0..4)<S> | Missing result:ussa=dynamic{1}[0..4)<S> |
| smart_pointer.cpp:18:15:18:43 | //$ussa=dynamic{1}[0..4)<int> | Missing result:ussa=dynamic{1}[0..4)<int> |
| smart_pointer.cpp:19:13:19:39 | //$ussa=dynamic{1}[0..4)<S> | Missing result:ussa=dynamic{1}[0..4)<S> |
| smart_pointer.cpp:20:21:20:47 | //$ussa=dynamic{1}[0..4)<S> | Missing result:ussa=dynamic{1}[0..4)<S> |
| smart_pointer.cpp:25:21:25:49 | //$ussa=dynamic{1}[0..4)<int> | Missing result:ussa=dynamic{1}[0..4)<int> |
| smart_pointer.cpp:26:14:26:40 | //$ussa=dynamic{1}[0..4)<S> | Missing result:ussa=dynamic{1}[0..4)<S> |
| smart_pointer.cpp:28:22:28:48 | //$ussa=dynamic{1}[0..4)<S> | Missing result:ussa=dynamic{1}[0..4)<S> |
| smart_pointer.cpp:30:15:30:43 | //$ussa=dynamic{1}[0..4)<int> | Missing result:ussa=dynamic{1}[0..4)<int> |
| smart_pointer.cpp:31:13:31:39 | //$ussa=dynamic{1}[0..4)<S> | Missing result:ussa=dynamic{1}[0..4)<S> |
| smart_pointer.cpp:32:21:32:47 | //$ussa=dynamic{1}[0..4)<S> | Missing result:ussa=dynamic{1}[0..4)<S> |
failures