// We might be live, depending on the liveness of Use.
return MarkIfNotLive(Use, MaybeLiveUses);
} else {
- DAE::Liveness Result;
+ DAE::Liveness Result = MaybeLive;
for (unsigned i = 0; i < NumRetVals(F); ++i) {
RetOrArg Use = CreateRet(F, i);
- // We might be live, depending on the liveness of Use. All Results
- // should be the same since they depend only on F.
- Result = MarkIfNotLive(Use, MaybeLiveUses);
+ // We might be live, depending on the liveness of Use. If any
+ // sub-value is live, then the entire value is considered live. This
+ // is a conservative choice, and better tracking is possible.
+ DAE::Liveness SubResult = MarkIfNotLive(Use, MaybeLiveUses);
+ if (Result != Live)
+ Result = SubResult;
}
return Result;
}
%ret = extractvalue {i32, i32} %val, 1
ret i32 %ret
}
+
+; Case 6: When considering @mid, the return instruciton has sub-value 0
+; unconditionally live, but 1 only conditionally live. Since at that level we're
+; applying the results to the whole of %res, this means %res is live and cannot
+; be reduced. There is scope for further optimisation here (though not visible
+; in this test-case).
+
+; CHECK-LABEL: define internal { i8*, i32 } @inner()
+
+define internal {i8*, i32} @mid() {
+ %res = call {i8*, i32} @inner()
+ %intval = extractvalue {i8*, i32} %res, 1
+ %tst = icmp eq i32 %intval, 42
+ br i1 %tst, label %true, label %true
+
+true:
+ ret {i8*, i32} %res
+}
+
+define internal {i8*, i32} @inner() {
+ ret {i8*, i32} {i8* null, i32 42}
+}
+
+define internal i8 @outer() {
+ %res = call {i8*, i32} @mid()
+ %resptr = extractvalue {i8*, i32} %res, 0
+
+ %val = load i8* %resptr
+ ret i8 %val
+}
\ No newline at end of file