Merge pull request #23723 from drodriguez/fix-network-service-handling

[windows] Fix handling of Network Service username.
diff --git a/include/swift/SILOptimizer/PassManager/Passes.def b/include/swift/SILOptimizer/PassManager/Passes.def
index fd89201..605e470 100644
--- a/include/swift/SILOptimizer/PassManager/Passes.def
+++ b/include/swift/SILOptimizer/PassManager/Passes.def
@@ -289,8 +289,8 @@
      "SIL retain/release Peephole Removal for Builtin.unsafeGuaranteed")
 PASS(UsePrespecialized, "use-prespecialized",
      "Use Pre-Specialized Functions")
-PASS(ValueOwnershipKindDumper, "value-ownership-kind-dumper",
-     "Print Value Ownership Kind for Testing")
+PASS(OwnershipDumper, "ownership-dumper",
+     "Print Ownership information for Testing")
 PASS(SemanticARCOpts, "semantic-arc-opts",
      "Semantic ARC Optimization")
 PASS(MarkUninitializedFixup, "mark-uninitialized-fixup",
diff --git a/lib/SILOptimizer/UtilityPasses/CMakeLists.txt b/lib/SILOptimizer/UtilityPasses/CMakeLists.txt
index 461b8a5..e5b4524 100644
--- a/lib/SILOptimizer/UtilityPasses/CMakeLists.txt
+++ b/lib/SILOptimizer/UtilityPasses/CMakeLists.txt
@@ -27,5 +27,5 @@
   SideEffectsDumper.cpp
   SimplifyUnreachableContainingBlocks.cpp
   StripDebugInfo.cpp
-  ValueOwnershipKindDumper.cpp
+  OwnershipDumper.cpp
 )
diff --git a/lib/SILOptimizer/UtilityPasses/OwnershipDumper.cpp b/lib/SILOptimizer/UtilityPasses/OwnershipDumper.cpp
new file mode 100644
index 0000000..70fc8f5
--- /dev/null
+++ b/lib/SILOptimizer/UtilityPasses/OwnershipDumper.cpp
@@ -0,0 +1,77 @@
+//===--- OwnershipDumper.cpp ----------------------------------------------===//
+//
+// This source file is part of the Swift.org open source project
+//
+// Copyright (c) 2014 - 2018 Apple Inc. and the Swift project authors
+// Licensed under Apache License v2.0 with Runtime Library Exception
+//
+// See https://swift.org/LICENSE.txt for license information
+// See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
+//
+//===----------------------------------------------------------------------===//
+///
+/// \file
+///
+/// This is a simple utility pass that dumps the ValueOwnershipKind of all
+/// SILValue in a module. It is meant to trigger assertions and verification of
+/// these values.
+///
+//===----------------------------------------------------------------------===//
+
+#include "swift/SIL/SILFunction.h"
+#include "swift/SIL/SILInstruction.h"
+#include "swift/SILOptimizer/PassManager/Passes.h"
+#include "swift/SILOptimizer/PassManager/Transforms.h"
+
+using namespace swift;
+
+//===----------------------------------------------------------------------===//
+//                               Implementation
+//===----------------------------------------------------------------------===//
+
+static void dumpInstruction(SILInstruction &ii) {
+  llvm::outs() << "Visiting: " << ii;
+
+  auto ops = ii.getAllOperands();
+  if (!ops.empty()) {
+    llvm::outs() << "Operand Ownership Map:\n";
+    for (const auto &op : ops) {
+      llvm::outs() << "Op #: " << op.getOperandNumber() << "\n"
+                   << "Ownership Map: " << op.getOwnershipKindMap();
+    }
+  }
+
+  // If the instruction doesn't have any results, bail.
+  auto results = ii.getResults();
+  if (!results.empty()) {
+    llvm::outs() << "Results Ownership Kinds:\n";
+    for (auto v : results) {
+      auto kind = v.getOwnershipKind();
+      llvm::outs() << "Result: " << v;
+      llvm::outs() << "Kind: " << kind << "\n";
+    }
+  }
+}
+
+//===----------------------------------------------------------------------===//
+//                            Top Level Entrypoint
+//===----------------------------------------------------------------------===//
+
+namespace {
+
+class OwnershipDumper : public SILFunctionTransform {
+  void run() override {
+    SILFunction *f = getFunction();
+    llvm::outs() << "*** Dumping Function: '" << f->getName() << "'\n";
+    for (auto &bb : *f) {
+      // We only dump instructions right now.
+      for (auto &ii : bb) {
+        dumpInstruction(ii);
+      }
+    }
+  }
+};
+
+} // end anonymous namespace
+
+SILTransform *swift::createOwnershipDumper() { return new OwnershipDumper(); }
diff --git a/lib/SILOptimizer/UtilityPasses/ValueOwnershipKindDumper.cpp b/lib/SILOptimizer/UtilityPasses/ValueOwnershipKindDumper.cpp
deleted file mode 100644
index 6d398bb..0000000
--- a/lib/SILOptimizer/UtilityPasses/ValueOwnershipKindDumper.cpp
+++ /dev/null
@@ -1,63 +0,0 @@
-//===--- ValueOwnershipKindDumper.cpp -------------------------------------===//
-//
-// This source file is part of the Swift.org open source project
-//
-// Copyright (c) 2014 - 2017 Apple Inc. and the Swift project authors
-// Licensed under Apache License v2.0 with Runtime Library Exception
-//
-// See https://swift.org/LICENSE.txt for license information
-// See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
-//
-//===----------------------------------------------------------------------===//
-///
-/// This is a simple utility pass that dumps the ValueOwnershipKind of all
-/// SILValue in a module. It is meant to trigger assertions and verification of
-/// these values.
-///
-//===----------------------------------------------------------------------===//
-
-#include "swift/SIL/SILFunction.h"
-#include "swift/SIL/SILInstruction.h"
-#include "swift/SILOptimizer/PassManager/Passes.h"
-#include "swift/SILOptimizer/PassManager/Transforms.h"
-
-using namespace swift;
-
-namespace {
-
-class ValueOwnershipKindDumper : public SILFunctionTransform {
-
-  void run() override {
-    SILFunction *F = getFunction();
-    for (auto &BB : *F) {
-      // We only verify instructions right now.
-      for (auto &II : BB) {
-        // If the instruction doesn't have any results, bail.
-        auto results = II.getResults();
-        if (results.empty())
-          continue;
-
-        llvm::outs() << "Visiting: " << II;
-
-        for (auto V : results) {
-          auto Kind = V.getOwnershipKind();
-          llvm::outs() << "    " << Kind << "\n";
-          if (Kind == ValueOwnershipKind::Any)
-            continue;
-
-          if (V->getType().isTrivial(*F)) {
-            llvm_unreachable(
-                "Error! Non Trivial ownership with trivial type\n");
-          }
-        }
-      }
-    }
-  }
-
-};
-
-} // end anonymous namespace
-
-SILTransform *swift::createValueOwnershipKindDumper() {
-  return new ValueOwnershipKindDumper();
-}
diff --git a/lib/SILOptimizer/Utils/ConstantFolding.cpp b/lib/SILOptimizer/Utils/ConstantFolding.cpp
index cfebd85..7811d4f 100644
--- a/lib/SILOptimizer/Utils/ConstantFolding.cpp
+++ b/lib/SILOptimizer/Utils/ConstantFolding.cpp
@@ -278,6 +278,44 @@
            ResultsInError);
 }
 
+static SILValue countZeros(BuiltinInst *BI, llvm::Intrinsic::ID ID) {
+  assert(BI->getArguments().size() == 2 && "Ctlz should have 2 args.");
+  OperandValueArrayRef Args = BI->getArguments();
+
+  // Fold for integer constant arguments.
+  auto *LHS = dyn_cast<IntegerLiteralInst>(Args[0]);
+  if (!LHS) {
+    return nullptr;
+  }
+  APInt LHSI = LHS->getValue();
+  unsigned LZ = 0;
+  // Check corner-case of source == zero
+  if (LHSI == 0) {
+    auto *RHS = dyn_cast<IntegerLiteralInst>(Args[1]);
+    if (!RHS || RHS->getValue() != 0) {
+      // Undefined
+      return nullptr;
+    }
+    LZ = LHSI.getBitWidth();
+  } else {
+    switch (ID) {
+    default:
+      return nullptr;
+    case llvm::Intrinsic::ctlz: {
+      LZ = LHSI.countLeadingZeros();
+      break;
+    }
+    case llvm::Intrinsic::cttz: {
+      LZ = LHSI.countTrailingZeros();
+      break;
+    }
+    }
+  }
+  APInt LZAsAPInt = APInt(LHSI.getBitWidth(), LZ);
+  SILBuilderWithScope B(BI);
+  return B.createIntegerLiteral(BI->getLoc(), LHS->getType(), LZAsAPInt);
+}
+
 static SILValue constantFoldIntrinsic(BuiltinInst *BI, llvm::Intrinsic::ID ID,
                                       Optional<bool> &ResultsInError) {
   switch (ID) {
@@ -291,31 +329,9 @@
     return Op1;
   }
 
-  case llvm::Intrinsic::ctlz: {
-    assert(BI->getArguments().size() == 2 && "Ctlz should have 2 args.");
-    OperandValueArrayRef Args = BI->getArguments();
-
-    // Fold for integer constant arguments.
-    auto *LHS = dyn_cast<IntegerLiteralInst>(Args[0]);
-    if (!LHS) {
-      return nullptr;
-    }
-    APInt LHSI = LHS->getValue();
-    unsigned LZ = 0;
-    // Check corner-case of source == zero
-    if (LHSI == 0) {
-      auto *RHS = dyn_cast<IntegerLiteralInst>(Args[1]);
-      if (!RHS || RHS->getValue() != 0) {
-        // Undefined
-        return nullptr;
-      }
-      LZ = LHSI.getBitWidth();
-    } else {
-      LZ = LHSI.countLeadingZeros();
-    }
-    APInt LZAsAPInt = APInt(LHSI.getBitWidth(), LZ);
-    SILBuilderWithScope B(BI);
-    return B.createIntegerLiteral(BI->getLoc(), LHS->getType(), LZAsAPInt);
+  case llvm::Intrinsic::ctlz:
+  case llvm::Intrinsic::cttz: {
+    return countZeros(BI, ID);
   }
 
   case llvm::Intrinsic::sadd_with_overflow:
diff --git a/test/ClangImporter/long-long-promotion.swift b/test/ClangImporter/long-long-promotion.swift
new file mode 100644
index 0000000..d700855
--- /dev/null
+++ b/test/ClangImporter/long-long-promotion.swift
@@ -0,0 +1,16 @@
+// RUN: %target-swift-frontend(mock-sdk: %clang-importer-sdk) -typecheck -verify %s
+
+import macros
+
+func verifyIsSigned(_: Int64) { }
+func verifyIsUnsigned(_: UInt64) { }
+
+// Windows will not convert a long long value that overflows into an unsigned
+// long long if it has the `ll` suffix of `i64` suffix.  Ensure that the type is
+// imported appropriately.
+#if os(Windows)
+verifyIsSigned(LL_TO_ULL)
+#else
+verifyIsUnsigned(LL_TO_ULL)
+#endif
+
diff --git a/test/Inputs/clang-importer-sdk/usr/include/macros.h b/test/Inputs/clang-importer-sdk/usr/include/macros.h
index 537c832..60865ec 100644
--- a/test/Inputs/clang-importer-sdk/usr/include/macros.h
+++ b/test/Inputs/clang-importer-sdk/usr/include/macros.h
@@ -25,6 +25,8 @@
 #define TRUE 1
 #define FALSE 0
 
+#define LL_TO_ULL 0x8000000000000000LL
+
 #define A_PI M_PI
 
 #define VERSION_STRING "Swift 1.0"
diff --git a/test/SILOptimizer/constant_propagation.sil b/test/SILOptimizer/constant_propagation.sil
index c1897b2..7283129 100644
--- a/test/SILOptimizer/constant_propagation.sil
+++ b/test/SILOptimizer/constant_propagation.sil
@@ -50,6 +50,36 @@
 // CHECK-NEXT: return [[RES]] : $Builtin.Int64
 }
 
+sil @count_trailing_zeros_corner_case : $@convention(thin) () -> Builtin.Int64 {
+bb0:
+ %zero64 = integer_literal $Builtin.Int64, 0
+ %zero1 = integer_literal $Builtin.Int1, 0
+ %cttz = builtin "int_cttz_Int64"(%zero64 : $Builtin.Int64, %zero1 : $Builtin.Int1) : $Builtin.Int64
+ return %cttz : $Builtin.Int64
+
+// CHECK-LABEL: sil @count_trailing_zeros_corner_case
+// CHECK-NOT: integer_literal $Builtin.Int64, 0
+// CHECK-NOT: integer_literal $Builtin.Int1, 0
+// CHECK-NOT: builtin
+// CHECK: [[RES:%.*]] = integer_literal $Builtin.Int64, 64
+// CHECK-NEXT: return [[RES]] : $Builtin.Int64
+}
+
+sil @count_trailing_zeros : $@convention(thin) () -> Builtin.Int64 {
+bb0:
+ %zero64 = integer_literal $Builtin.Int64, 2
+ %zero1 = integer_literal $Builtin.Int1, 0
+ %cttz = builtin "int_cttz_Int64"(%zero64 : $Builtin.Int64, %zero1 : $Builtin.Int1) : $Builtin.Int64
+ return %cttz : $Builtin.Int64
+
+// CHECK-LABEL: sil @count_trailing_zeros
+// CHECK-NOT: integer_literal $Builtin.Int64, 2
+// CHECK-NOT: integer_literal $Builtin.Int1, 0
+// CHECK-NOT: builtin
+// CHECK: [[RES:%.*]] = integer_literal $Builtin.Int64, 1
+// CHECK-NEXT: return [[RES]] : $Builtin.Int64
+}
+
 // Compute an expression using a chain of arithmetic with overflow instructions: 2 * (2 + 3) - 3
 sil @fold_arithmetic_with_overflow : $@convention(thin) () -> Builtin.Int64 {
 bb0:
diff --git a/test/SILOptimizer/ownership-kind-dumper.sil b/test/SILOptimizer/ownership-kind-dumper.sil
new file mode 100644
index 0000000..274eb9f
--- /dev/null
+++ b/test/SILOptimizer/ownership-kind-dumper.sil
@@ -0,0 +1,35 @@
+// RUN: %target-sil-opt -ownership-dumper %s -o /dev/null | %FileCheck %s
+
+sil_stage canonical
+
+import Builtin
+
+class Klass {}
+
+// CHECK-LABEL: Dumping Function: 'foo'
+// CHECK: Visiting:   %1 = unchecked_ref_cast %0 : $Builtin.NativeObject to $Klass
+// CHECK: Operand Ownership Map:
+// CHECK: Op #: 0
+// CHECK: Ownership Map: -- OperandOwnershipKindMap --
+// CHECK: unowned:  No.
+// CHECK: owned: Yes. Liveness: MustBeInvalidated
+// CHECK: guaranteed:  No.
+// CHECK: any: Yes. Liveness: MustBeLive
+// CHECK: Results Ownership Kinds:
+// CHECK: Result:   %1 = unchecked_ref_cast %0 : $Builtin.NativeObject to $Klass
+// CHECK: Kind: owned
+// CHECK: Visiting:   return %1 : $Klass
+// CHECK: Operand Ownership Map:
+// CHECK: Op #: 0
+// CHECK: Ownership Map: -- OperandOwnershipKindMap --
+// CHECK: unowned:  No.
+// CHECK: owned: Yes. Liveness: MustBeInvalidated
+// CHECK: guaranteed:  No.
+// CHECK: any: Yes. Liveness: MustBeLive
+sil [ossa] @foo : $@convention(thin) (@owned Builtin.NativeObject) -> @owned Klass {
+bb0(%0 : @owned $Builtin.NativeObject):
+  %1 = unchecked_ref_cast %0 : $Builtin.NativeObject to $Klass
+  return %1 : $Klass
+}
+
+