mirror of
https://github.com/apple/swift.git
synced 2025-12-21 12:14:44 +01:00
<rdar://problem/20402026> Remove scope entry/exit log entries
Don't emit scope entry/exit logging code in instrumentation for playgrounds if -playground-high-performance option is passed. Swift SVN r27046
This commit is contained in:
@@ -196,6 +196,10 @@ public:
|
||||
/// Indicates whether the playground transformation should be applied.
|
||||
bool PlaygroundTransform = false;
|
||||
|
||||
/// Indicates whether the playground transformation should omit
|
||||
/// instrumentation that has a high runtime performance impact.
|
||||
bool PlaygroundHighPerformance = false;
|
||||
|
||||
/// Indicates whether standard help should be shown.
|
||||
bool PrintHelp = false;
|
||||
|
||||
|
||||
@@ -209,6 +209,9 @@ def print_stats : Flag<["-"], "print-stats">,
|
||||
def playground : Flag<["-"], "playground">,
|
||||
HelpText<"Apply the playground semantics and transformation">;
|
||||
|
||||
def playground_high_performance : Flag<["-"], "playground-high-performance">,
|
||||
HelpText<"Omit instrumentation that has a high runtime performance impact">;
|
||||
|
||||
def disable_playground_transform : Flag<["-"], "disable-playground-transform">,
|
||||
HelpText<"Disable playground transformation">;
|
||||
|
||||
|
||||
@@ -133,7 +133,10 @@ namespace swift {
|
||||
|
||||
/// Once parsing and name-binding are complete, this optionally transforms the
|
||||
/// ASTs to add calls to external logging functions.
|
||||
void performPlaygroundTransform(SourceFile &SF);
|
||||
///
|
||||
/// \param HighPerformance True if the playground transform should omit
|
||||
/// instrumentation that has a high runtime performance impact.
|
||||
void performPlaygroundTransform(SourceFile &SF, bool HighPerformance);
|
||||
|
||||
/// Flags used to control type checking.
|
||||
enum class TypeCheckingFlags : unsigned {
|
||||
|
||||
@@ -112,6 +112,8 @@ static bool ParseFrontendArgs(FrontendOptions &Opts, ArgList &Args,
|
||||
Opts.PlaygroundTransform |= Args.hasArg(OPT_playground);
|
||||
if (Args.hasArg(OPT_disable_playground_transform))
|
||||
Opts.PlaygroundTransform = false;
|
||||
Opts.PlaygroundHighPerformance |=
|
||||
Args.hasArg(OPT_playground_high_performance);
|
||||
|
||||
if (const Arg *A = Args.getLastArg(OPT_help, OPT_help_hidden)) {
|
||||
if (A->getOption().matches(OPT_help)) {
|
||||
|
||||
@@ -425,7 +425,7 @@ void CompilerInstance::performSema() {
|
||||
} while (!Done);
|
||||
|
||||
if (mainIsPrimary && Invocation.getFrontendOptions().PlaygroundTransform)
|
||||
performPlaygroundTransform(MainFile);
|
||||
performPlaygroundTransform(MainFile, Invocation.getFrontendOptions().PlaygroundHighPerformance);
|
||||
if (!mainIsPrimary)
|
||||
performNameBinding(MainFile);
|
||||
}
|
||||
|
||||
@@ -45,6 +45,7 @@ private:
|
||||
ASTContext &Context;
|
||||
DeclContext *TypeCheckDC;
|
||||
unsigned TmpNameIndex = 0;
|
||||
bool HighPerformance;
|
||||
|
||||
struct BracePair {
|
||||
public:
|
||||
@@ -110,6 +111,9 @@ private:
|
||||
// all the braces up to its target.
|
||||
size_t escapeToTarget(BracePair::TargetKinds TargetKind,
|
||||
ElementVector &Elements, size_t EI) {
|
||||
if (HighPerformance)
|
||||
return EI;
|
||||
|
||||
for (const BracePair &BP : BracePairs) {
|
||||
if (BP.TargetKind == TargetKind) {
|
||||
break;
|
||||
@@ -151,8 +155,9 @@ private:
|
||||
ClosureFinder CF;
|
||||
|
||||
public:
|
||||
Instrumenter (ASTContext &C, DeclContext *DC, std::mt19937_64 &RNG) :
|
||||
RNG(RNG), Context(C), TypeCheckDC(DC), CF(*this) { }
|
||||
Instrumenter (ASTContext &C, DeclContext *DC, std::mt19937_64 &RNG,
|
||||
bool HP) :
|
||||
RNG(RNG), Context(C), TypeCheckDC(DC), HighPerformance(HP), CF(*this) { }
|
||||
|
||||
Stmt *transformStmt(Stmt *S) {
|
||||
switch (S->getKind()) {
|
||||
@@ -558,7 +563,7 @@ public:
|
||||
}
|
||||
}
|
||||
|
||||
if (!TopLevel) {
|
||||
if (!TopLevel && !HighPerformance) {
|
||||
Elements.insert(Elements.begin(), buildScopeEntry(BS->getSourceRange()));
|
||||
Elements.insert(Elements.end(), buildScopeExit(BS->getSourceRange()));
|
||||
}
|
||||
@@ -579,7 +584,8 @@ public:
|
||||
}
|
||||
|
||||
// log*() functions return a newly-created log expression to be inserted
|
||||
// after or instead of the expression they're looking at.
|
||||
// after or instead of the expression they're looking at. Only call this
|
||||
// if the variable has an initializer.
|
||||
Expr *logVarDecl(VarDecl *VD) {
|
||||
if (llvm::dyn_cast<ConstructorDecl>(TypeCheckDC) &&
|
||||
VD->getNameStr().equals("self")) {
|
||||
@@ -812,16 +818,20 @@ public:
|
||||
|
||||
} // end anonymous namespace
|
||||
|
||||
void swift::performPlaygroundTransform(SourceFile &SF) {
|
||||
void swift::performPlaygroundTransform(SourceFile &SF,
|
||||
bool HighPerformance) {
|
||||
class ExpressionFinder : public ASTWalker {
|
||||
private:
|
||||
std::mt19937_64 RNG;
|
||||
bool HighPerformance;
|
||||
public:
|
||||
ExpressionFinder(bool HP) : HighPerformance(HP) { }
|
||||
|
||||
virtual bool walkToDeclPre(Decl *D) {
|
||||
if (AbstractFunctionDecl *FD = llvm::dyn_cast<AbstractFunctionDecl>(D)) {
|
||||
if (!FD->isImplicit()) {
|
||||
if (BraceStmt *Body = FD->getBody()) {
|
||||
Instrumenter I(FD->getASTContext(), FD, RNG);
|
||||
Instrumenter I(FD->getASTContext(), FD, RNG, HighPerformance);
|
||||
BraceStmt *NewBody = I.transformBraceStmt(Body);
|
||||
if (NewBody != Body) {
|
||||
FD->setBody(NewBody);
|
||||
@@ -832,7 +842,7 @@ void swift::performPlaygroundTransform(SourceFile &SF) {
|
||||
} else if (TopLevelCodeDecl *TLCD = llvm::dyn_cast<TopLevelCodeDecl>(D)) {
|
||||
if (!TLCD->isImplicit()) {
|
||||
if (BraceStmt *Body = TLCD->getBody()) {
|
||||
Instrumenter I(((Decl*)TLCD)->getASTContext(), TLCD, RNG);
|
||||
Instrumenter I(((Decl*)TLCD)->getASTContext(), TLCD, RNG, HighPerformance);
|
||||
BraceStmt *NewBody = I.transformBraceStmt(Body, true);
|
||||
if (NewBody != Body) {
|
||||
TLCD->setBody(NewBody);
|
||||
@@ -845,7 +855,7 @@ void swift::performPlaygroundTransform(SourceFile &SF) {
|
||||
}
|
||||
};
|
||||
|
||||
ExpressionFinder EF;
|
||||
ExpressionFinder EF(HighPerformance);
|
||||
for (Decl* D : SF.Decls) {
|
||||
D->walk(EF);
|
||||
}
|
||||
|
||||
39
test/PlaygroundTransform/high_performance.swift
Normal file
39
test/PlaygroundTransform/high_performance.swift
Normal file
@@ -0,0 +1,39 @@
|
||||
// RUN: rm -rf %t
|
||||
// RUN: mkdir %t
|
||||
// RUN: cp %s %t/main.swift
|
||||
// RUN: %target-build-swift -Xfrontend -playground -Xfrontend -playground-high-performance -Xfrontend -debugger-support -o %t/main %S/Inputs/PlaygroundsRuntime.swift %t/main.swift
|
||||
// RUN: %target-run %t/main | FileCheck %s
|
||||
|
||||
var a = true
|
||||
if (a) {
|
||||
5
|
||||
} else {
|
||||
7
|
||||
}
|
||||
|
||||
for i in 0..<3 {
|
||||
i
|
||||
}
|
||||
// CHECK: [{{.*}}] $builtin_log[a='true']
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[='5']
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[='0']
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[='1']
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[='2']
|
||||
|
||||
var b = true
|
||||
for i in 0..<3 {
|
||||
i
|
||||
continue
|
||||
}
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[b='true']
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[='0']
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[='1']
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[='2']
|
||||
|
||||
var c = true
|
||||
for i in 0..<3 {
|
||||
i
|
||||
break
|
||||
}
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[c='true']
|
||||
// CHECK-NEXT: [{{.*}}] $builtin_log[='0']
|
||||
Reference in New Issue
Block a user