blob: da9f6c4b17cf65fe4a6e0b993fc28cbd1721294c [file] [log] [blame]
// RUN: %empty-directory(%t)
// RUN: %target-build-swift %s -o %t/a.out
// RUN: %target-codesign %t/a.out
// RUN: %target-run %t/a.out | %FileCheck %s
// REQUIRES: executable_test
enum Singleton {
case x(Int, UnicodeScalar)
}
enum NoPayload {
case x
case y
case z
}
enum SinglePayloadTrivial {
case x(UnicodeScalar, Int)
case y
case z
}
enum MultiPayloadTrivial {
case x(UnicodeScalar, Int)
case y(Int, Double)
case z
}
var s = Singleton.x(1, "a")
switch s {
case .x(var int, var char):
// CHECK: 1
print(int)
// CHECK: a
print(char)
}
func printNoPayload(_ v: NoPayload) {
switch v {
case .x:
print("NoPayload.x")
case .y:
print("NoPayload.y")
case .z:
print("NoPayload.z")
}
}
// CHECK: NoPayload.x
printNoPayload(.x)
// CHECK: NoPayload.y
printNoPayload(.y)
// CHECK: NoPayload.z
printNoPayload(.z)
func printSinglePayloadTrivial(_ v: SinglePayloadTrivial) {
switch v {
case .x(let char, let int):
print("SinglePayloadTrivial.x(\(char), \(int))")
case .y:
print("SinglePayloadTrivial.y")
case .z:
print("SinglePayloadTrivial.z")
}
}
// CHECK: SinglePayloadTrivial.x(b, 2)
printSinglePayloadTrivial(.x("b", 2))
// CHECK: SinglePayloadTrivial.y
printSinglePayloadTrivial(.y)
// CHECK: SinglePayloadTrivial.z
printSinglePayloadTrivial(.z)
func printMultiPayloadTrivial(_ v: MultiPayloadTrivial) {
switch v {
case .x(let char, let int):
print("MultiPayloadTrivial.x(\(char), \(int))")
case .y(let int, let double):
print("MultiPayloadTrivial.y(\(int), \(double))")
case .z:
print("MultiPayloadTrivial.z")
}
}
// CHECK: MultiPayloadTrivial.x(c, 3)
printMultiPayloadTrivial(.x("c", 3))
// CHECK: MultiPayloadTrivial.y(4, 5.5)
printMultiPayloadTrivial(.y(4, 5.5))
// CHECK: MultiPayloadTrivial.z
printMultiPayloadTrivial(.z)
protocol Runcible {
func runce()
}
struct Spoon : Runcible {
var xxx = 0
func runce() { print("Spoon!") }
}
struct Hat : Runcible {
var xxx : Float = 0
func runce() { print("Hat!") }
}
enum SinglePayloadAddressOnly {
case x(Runcible)
case y
}
func printSinglePayloadAddressOnly(_ v: SinglePayloadAddressOnly) {
switch v {
case .x(let runcible):
runcible.runce()
case .y:
print("Why?")
}
}
// CHECK: Spoon!
printSinglePayloadAddressOnly(.x(Spoon()))
// CHECK: Hat!
printSinglePayloadAddressOnly(.x(Hat()))
// CHECK: Why?
printSinglePayloadAddressOnly(.y)
enum MultiPayloadAddressOnly {
case x(Runcible)
case y(String, Runcible)
case z
}
func printMultiPayloadAddressOnly(_ v: MultiPayloadAddressOnly) {
switch v {
case .x(let runcible):
runcible.runce()
case .y(let s, let runcible):
print("\(s) ", terminator: "")
runcible.runce()
case .z:
print("Zed.")
}
}
// CHECK: Spoon!
printMultiPayloadAddressOnly(.x(Spoon()))
// CHECK: Porkpie Hat!
printMultiPayloadAddressOnly(.y("Porkpie", Hat()))
// CHECK: Zed.
printMultiPayloadAddressOnly(.z)
enum TrivialGeneric<T, U> {
case x(T, U)
}
func unwrapTrivialGeneric<T, U>(_ tg: TrivialGeneric<T, U>) -> (T, U) {
switch tg {
case .x(let t, let u):
return (t, u)
}
}
func wrapTrivialGeneric<T, U>(_ t: T, _ u: U) -> TrivialGeneric<T, U> {
return .x(t, u)
}
var tg : TrivialGeneric<Int, String> = .x(23, "skidoo")
// CHECK: 23 skidoo
switch tg {
case .x(let t, let u):
print("\(t) \(u)")
}
// CHECK: 413 dream
switch unwrapTrivialGeneric(.x(413, "dream")) {
case (let t, let u):
print("\(t) \(u)")
}
// CHECK: 1 is the loneliest number that you'll ever do
switch wrapTrivialGeneric(1, "is the loneliest number that you'll ever do") {
case .x(let t, let u):
print("\(t) \(u)")
}
enum Ensemble<S : Runcible, H : Runcible> {
case x(S, H)
}
func concreteEnsemble(_ e: Ensemble<Spoon, Hat>) {
switch e {
case .x(let spoon, let hat):
spoon.runce()
hat.runce()
}
}
func genericEnsemble<T : Runcible, U : Runcible>(_ e: Ensemble<T, U>) {
switch e {
case .x(let t, let u):
t.runce()
u.runce()
}
}
// CHECK: Spoon!
// CHECK: Hat!
concreteEnsemble(.x(Spoon(), Hat()))
// CHECK: Spoon!
// CHECK: Hat!
genericEnsemble(.x(Spoon(), Hat()))
// CHECK: Spoon!
// CHECK: Spoon!
genericEnsemble(.x(Spoon(), Spoon()))
// CHECK: Hat!
// CHECK: Spoon!
genericEnsemble(.x(Hat(), Spoon()))
enum Optionable<T> {
case Mere(T)
case Nought
init() { self = .Nought }
init(_ x:T) { self = .Mere(x) }
}
func tryRunce<T : Runcible>(_ x: Optionable<T>) {
switch x {
case .Mere(let r):
r.runce()
case .Nought:
print("nought")
}
}
// CHECK: Spoon!
tryRunce(.Mere(Spoon()))
// CHECK: Hat!
tryRunce(.Mere(Hat()))
// CHECK: nought
tryRunce(Optionable<Spoon>.Nought)
// CHECK: nought
tryRunce(Optionable<Hat>.Nought)
// CHECK: Spoon!
tryRunce(Optionable(Spoon()))
// CHECK: Hat!
tryRunce(Optionable(Hat()))
func optionableInts() {
let optionables: [Optionable<Int>] = [
.Mere(219),
.Nought,
.Nought,
.Mere(20721)
]
for o in optionables {
switch o {
case .Mere(let x):
print(x)
case .Nought:
print("---")
}
}
}
// CHECK-LABEL: Optionable ints:
// CHECK: 219
// CHECK: ---
// CHECK: ---
// CHECK: 20721
print("Optionable ints:")
optionableInts()
enum Suit { case Spades, Hearts, Diamonds, Clubs }
func print(_ suit: Suit) {
switch suit {
case .Spades:
print("â™ ")
case .Hearts:
print("♡")
case .Diamonds:
print("♢")
case .Clubs:
print("♣")
}
}
func optionableSuits() {
let optionables: [Optionable<Suit>] = [
.Mere(.Spades),
.Mere(.Diamonds),
.Nought,
.Mere(.Hearts)
]
for o in optionables {
switch o {
case .Mere(let x):
print(x)
case .Nought:
print("---")
}
}
}
// CHECK: â™ 
// CHECK: ♢
// CHECK: ---
// CHECK: ♡
optionableSuits()
func optionableRuncibles<T : Runcible>(_ x: T) {
let optionables: [Optionable<T>] = [
.Mere(x),
.Nought,
.Mere(x),
.Nought
]
for o in optionables {
switch o {
case .Mere(let x):
x.runce()
case .Nought:
print("---")
}
}
}
// CHECK: Spoon!
// CHECK: ---
// CHECK: Spoon!
// CHECK: ---
optionableRuncibles(Spoon())
// CHECK: Hat!
// CHECK: ---
// CHECK: Hat!
// CHECK: ---
optionableRuncibles(Hat())
// <rdar://problem/15383966>
protocol ClassProtocol : class {}
class Rdar15383966 : ClassProtocol
{
var id : Int
init(_ anID : Int) {
print("X(\(anID))")
id = anID
}
deinit {
print("~X(\(id))")
}
}
func generic<T>(_ x: T?) { }
func generic_over_classes<T : ClassProtocol>(_ x: T?) { }
func nongeneric(_ x: Rdar15383966?) { }
func test_generic()
{
var x: Rdar15383966? = Rdar15383966(1)
generic(x)
x = .none
generic(x)
}
// CHECK: X(1)
// CHECK: ~X(1)
test_generic()
func test_nongeneric()
{
var x: Rdar15383966? = Rdar15383966(2)
nongeneric(x)
x = .none
nongeneric(x)
}
// CHECK: X(2)
// CHECK: ~X(2)
test_nongeneric()
func test_generic_over_classes()
{
var x: Rdar15383966? = Rdar15383966(3)
generic_over_classes(x)
x = .none
generic_over_classes(x)
}
// CHECK: X(3)
// CHECK: ~X(3)
test_generic_over_classes()
struct S {
var a: Int32; var b: Int64
init(_ a: Int32, _ b: Int64) {
self.a = a
self.b = b
}
}
enum MultiPayloadSpareBitAggregates {
case x(Int32, Int64)
case y(Rdar15383966, Rdar15383966)
case z(S)
}
func test_spare_bit_aggregate(_ x: MultiPayloadSpareBitAggregates) {
switch x {
case .x(let i32, let i64):
print(".x(\(i32), \(i64))")
case .y(let a, let b):
print(".y(\(a.id), \(b.id))")
case .z(let s):
print(".z(\(s))")
}
}
print("---")
// CHECK: .x(22, 44)
test_spare_bit_aggregate(.x(22, 44))
// CHECK: X(222)
// CHECK: X(444)
// CHECK: .y(222, 444)
// CHECK-DAG: ~X(222)
// CHECK-DAG: ~X(444)
test_spare_bit_aggregate(.y(Rdar15383966(222), Rdar15383966(444)))
// CHECK: .z(S(a: 333, b: 666))
test_spare_bit_aggregate(.z(S(333, 666)))
print("---")
struct OptionalTuple<T> {
var value : (T, T)?
init(_ value: (T, T)?) {
self.value = value
}
}
func test_optional_generic_tuple<T>(_ a: OptionalTuple<T>) -> T {
print("optional pair is same size as pair: \(MemoryLayout.size(ofValue: a) == MemoryLayout<T>.size*2)")
return a.value!.0
}
print("Int result: \(test_optional_generic_tuple(OptionalTuple<Int>((5, 6))))")
// CHECK: optional pair is same size as pair: false
// CHECK: Int result: 5
class AnyOldClass {
var x: Int
init(_ value: Int) { x = value }
}
print("class result: \(test_optional_generic_tuple(OptionalTuple((AnyOldClass(10), AnyOldClass(11)))).x)")
// CHECK: optional pair is same size as pair: true
// CHECK: class result: 10
// <rdar://problem/16887421>
// CHECK-LABEL: Optional equality:
print("Optional equality:")
// CHECK: true
print((NoPayload.x as NoPayload?) == NoPayload.x)
// CHECK: false
print((NoPayload.x as NoPayload?) == NoPayload.y)
// rdar://problem/17814752
class Foo {}
struct Oof {
weak var foo: Foo?
}
protocol Boo {}
struct Goof {
var boo: Boo?
}
let oofs = [Oof()]
let goofs = [Goof()]
enum Planet: String {
case Mercury = "Mercury", Venus = "Venus", Mars
init() {
self = Planet.Venus
}
}
var pl1 = Planet()
print(pl1.rawValue)
// CHECK: {{^Venus$}}
print(Planet.Mars.rawValue)
// CHECK: {{^Mars$}}
enum EitherOr<T, U> {
case Left(T)
case Middle
case Center
case Right(U)
}
@inline(never)
func presentEitherOr<T, U>(_ e: EitherOr<T, U>) {
switch e {
case .Left(let l):
print("Left(\(l))")
case .Right(let r):
print("Right(\(r))")
case .Middle:
print("Middle")
case .Center:
print("Center")
}
}
@inline(never)
func presentEitherOrsOf<T, U>(t: T, u: U) {
presentEitherOr(EitherOr<T, U>.Left(t))
presentEitherOr(EitherOr<T, U>.Middle)
presentEitherOr(EitherOr<T, U>.Center)
presentEitherOr(EitherOr<T, U>.Right(u))
}
presentEitherOr(EitherOr<(), ()>.Left(())) // CHECK-NEXT: Left(())
presentEitherOr(EitherOr<(), ()>.Middle) // CHECK-NEXT: Middle
presentEitherOr(EitherOr<(), ()>.Center) // CHECK-NEXT: Center
presentEitherOr(EitherOr<(), ()>.Right(())) // CHECK-NEXT: Right(())
// CHECK-NEXT: Left(())
// CHECK-NEXT: Middle
// CHECK-NEXT: Center
// CHECK-NEXT: Right(())
presentEitherOrsOf(t: (), u: ())
presentEitherOr(EitherOr<Int, String>.Left(1)) // CHECK-NEXT: Left(1)
presentEitherOr(EitherOr<Int, String>.Middle) // CHECK-NEXT: Middle
presentEitherOr(EitherOr<Int, String>.Center) // CHECK-NEXT: Center
presentEitherOr(EitherOr<Int, String>.Right("foo")) // CHECK-NEXT: Right(foo)
// CHECK-NEXT: Left(1)
// CHECK-NEXT: Middle
// CHECK-NEXT: Center
// CHECK-NEXT: Right(foo)
presentEitherOrsOf(t: 1, u: "foo")
presentEitherOr(EitherOr<(), String>.Left(())) // CHECK-NEXT: Left(())
presentEitherOr(EitherOr<(), String>.Middle) // CHECK-NEXT: Middle
presentEitherOr(EitherOr<(), String>.Center) // CHECK-NEXT: Center
presentEitherOr(EitherOr<(), String>.Right("foo")) // CHECK-NEXT: Right(foo)
// CHECK-NEXT: Left(())
// CHECK-NEXT: Middle
// CHECK-NEXT: Center
// CHECK-NEXT: Right(foo)
presentEitherOrsOf(t: (), u: "foo")
// SR-5148
enum Payload {
case email
}
enum Test {
case a
indirect case b(Payload)
}
@inline(never)
func printA() {
print("an a")
}
@inline(never)
func printB() {
print("an b")
}
@inline(never)
func testCase(_ testEmail: Test) {
switch testEmail {
case .a:
printA()
case .b:
printB()
}
}
@inline(never)
func createTestB() -> Test {
return Test.b(.email)
}
@inline(never)
func createTestA() -> Test {
return Test.a
}
// CHECK-NEXT: an b
testCase(createTestB())
// CHECK-NEXT: b(a.Payload.email)
print(createTestB())
// CHECK-NEXT: a
print(createTestA())
// CHECK-NEXT: done
print("done")
public enum MyOptional<T> {
case Empty
case SecondEmpty
case Some(T)
}
public class StopSpecialization {
public func generate<T>(_ e: T) -> MyOptional<T> {
return MyOptional.Some(e)
}
public func generate2<T>(_ e: T) -> MyOptional<T> {
return MyOptional.Empty
}
}
@inline(never)
func test(_ s : StopSpecialization, _ N: Int) -> Bool {
let x = s.generate(N)
switch x {
case .SecondEmpty:
return false
case .Empty:
return false
case .Some(_):
return true
}
}
@inline(never)
func test2(_ s : StopSpecialization, _ N: Int) -> Bool {
let x = s.generate2(N)
switch x {
case .SecondEmpty:
return false
case .Empty:
return true
case .Some(_):
return false
}
}
@inline(never)
func run() {
// CHECK: true
print(test(StopSpecialization(), 12))
// CHECK: true
print(test2(StopSpecialization(), 12))
}
run()
public enum Indirect<T> {
indirect case payload((T, other: T))
case none
}
public func testIndirectEnum<T>(_ payload: T) -> Indirect<T> {
return Indirect.payload((payload, other: payload))
}
public func testCase(_ closure: @escaping (Int) -> ()) -> Indirect<(Int) -> ()> {
return testIndirectEnum(closure)
}
// CHECK: payload((Function), other: (Function))
print(testCase({ _ in }))
enum MultiIndirectRef {
case empty
indirect case ind(Int)
case collection([Int])
}
struct Container {
var storage : MultiIndirectRef = .empty
mutating func adoptStyle(_ s: Int) {
storage = .ind(s)
}
}
func copyStorage(_ s: Int, _ x : Container) -> Container {
var c = x
c.adoptStyle(s)
return c
}
func testCase() {
let l = Container()
let c = copyStorage(5, l)
print(c)
}
// CHECK: Container(storage: a.MultiIndirectRef.ind(5))
testCase()