1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165
|
// REQUIRES: swift_swift_parser, executable_test
// RUN: %empty-directory(%t)
// RUN: %host-build-swift -swift-version 5 -emit-library -o %t/%target-library-name(MacroDefinition) -module-name=MacroDefinition %S/Inputs/syntax_macro_definitions.swift -g -no-toolchain-stdlib-rpath
// RUN: %target-typecheck-verify-swift -swift-version 5 -load-plugin-library %t/%target-library-name(MacroDefinition) -module-name MacroUser -DTEST_DIAGNOSTICS -swift-version 5
// RUN: %target-build-swift -swift-version 5 -load-plugin-library %t/%target-library-name(MacroDefinition) %s -o %t/main -module-name MacroUser -swift-version 5
// RUN: %target-codesign %t/main
// RUN: %target-run %t/main | %FileCheck %s
@attached(memberAttribute) macro wrapAllProperties() = #externalMacro(module: "MacroDefinition", type: "WrapAllProperties")
@attached(memberAttribute)
public macro wrapStoredProperties(_ attributeName: String) = #externalMacro(module: "MacroDefinition", type: "WrapStoredPropertiesMacro")
@propertyWrapper
struct Wrapper<T> {
init(wrappedValue: T) {
print("initializing wrapper with \(wrappedValue)")
self.wrappedValue = wrappedValue
}
var wrappedValue: T {
willSet { print("setting \(newValue)") }
}
}
protocol P {
func reading<EnclosingSelf, Value>(from keyPath: KeyPath<EnclosingSelf, Value>)
func writing<EnclosingSelf, Value>(to keyPath: KeyPath<EnclosingSelf, Value>)
}
extension P {
func reading<EnclosingSelf, Value>(from keyPath: KeyPath<EnclosingSelf, Value>) {
print("reading from key-path")
}
func writing<EnclosingSelf, Value>(to keyPath: KeyPath<EnclosingSelf, Value>) {
print("writing to key-path")
}
}
@propertyWrapper
struct EnclosingSelfWrapper<Value> {
private var stored: Value
init(wrappedValue: Value) { self.stored = wrappedValue }
@available(*, unavailable)
var wrappedValue: Value {
get { fatalError() }
set { fatalError() }
}
static subscript<EnclosingSelf: P>(
_enclosingInstance observed: EnclosingSelf,
wrapped wrappedKeyPath: ReferenceWritableKeyPath<EnclosingSelf, Value>,
storage storageKeyPath: ReferenceWritableKeyPath<EnclosingSelf, Self>
) -> Value {
get {
observed.reading(from: wrappedKeyPath)
return observed[keyPath: storageKeyPath].stored
}
set {
observed.writing(to: wrappedKeyPath)
observed[keyPath: storageKeyPath].stored = newValue
}
}
}
@wrapAllProperties
struct S {
var x: Int
var y: Int
}
// CHECK: initializing wrapper with 0
// CHECK: initializing wrapper with 1
var s = S(x: 0, y: 1)
// CHECK: setting 10
s.x = 10
// CHECK: setting 100
s.y = 100
@wrapAllProperties
class C: P {
var x: Int = 0
var y: Int = 0
}
var c = C()
// CHECK: reading from key-path
_ = c.x
// CHECK: reading from key-path
_ = c.y
// CHECK: writing to key-path
c.x = 10
// CHECK: writing to key-path
c.y = 100
// Use the "wrapStoredProperties" macro to deprecate all of the stored
// properties.
@wrapStoredProperties(#"available(*, deprecated, message: "hands off my data")"#)
struct OldStorage {
var x: Int
}
// The deprecation warning below comes from the deprecation attribute
// introduced by @wrapStoredProperties on OldStorage.
_ = OldStorage(x: 5).x // expected-warning{{'x' is deprecated: hands off my data}}
@wrapStoredProperties(#"available(*, deprecated, message: "hands off my data")"#)
class C2: P {
var x: Int = 0
var y: Int = 0
var squareOfLength: Int {
return x*x + y*y // expected-warning 4{{hands off my data}}
}
var blah: Int { squareOfLength }
}
@attached(member, names: named(expandedMember))
macro AddMember() = #externalMacro(module: "MacroDefinition", type: "SingleMemberMacro")
@AddMember
@wrapAllProperties
struct TestExpansionOrder {
var originalMember: Int = 10
}
var expansionOrder = TestExpansionOrder()
// CHECK-NOT: setting 27
expansionOrder.expandedMember = 27
// CHECK: setting 28
expansionOrder.originalMember = 28
#if TEST_DIAGNOSTICS
@wrapAllProperties
typealias A = Int
// expected-error@-2{{'memberAttribute' macro cannot be attached to type alias ('A')}}
@wrapAllProperties
func noMembers() {}
// expected-error@-2{{'memberAttribute' macro cannot be attached to global function ('noMembers')}}
#endif
@attached(memberAttribute)
public macro AddMemberPeers() = #externalMacro(module: "MacroDefinition", type: "AddMemberPeersMacro")
@attached(peer, names: suffixed(_special))
public macro _AddPeer() = #externalMacro(module: "MacroDefinition", type: "_AddPeerMacro")
@AddMemberPeers
struct User {
var name: String {
"mario"
}
}
|