@@ -184,71 +184,78 @@ struct AbsoluteRawSyntax {
184
184
}
185
185
}
186
186
187
- /// Indirect wrapper for a `Syntax` node to avoid cyclic inclusion of the
188
- /// `Syntax` struct in `SyntaxData`
189
- class SyntaxBox : CustomStringConvertible ,
190
- CustomDebugStringConvertible , TextOutputStreamable {
191
- let value : Syntax
187
+ /// SyntaxData is the underlying storage for each Syntax node.
188
+ ///
189
+ /// SyntaxData is an implementation detail, and should not be exposed to clients
190
+ /// of SwiftSyntax.
191
+ struct SyntaxData {
192
+ private enum Info {
193
+ case root( Root )
194
+ indirect case nonRoot( NonRoot )
195
+
196
+ // For root node.
197
+ struct Root {
198
+ var arena : SyntaxArena
199
+ }
192
200
193
- init ( _ value: Syntax ) {
194
- self . value = value
201
+ // For non-root nodes.
202
+ struct NonRoot {
203
+ var parent : SyntaxData
204
+ var absoluteInfo : AbsoluteSyntaxInfo
205
+ }
195
206
}
196
207
197
- // SyntaxBox should be transparent in all descriptions
208
+ private let info : Info
209
+ let raw : RawSyntax
198
210
199
- /// A source-accurate description of this node.
200
- var description : String {
201
- return value. description
211
+ private var rootInfo : Info . Root {
212
+ switch info {
213
+ case . root( let info) : return info
214
+ case . nonRoot( let info) : return info. parent. rootInfo
215
+ }
202
216
}
203
217
204
- /// Returns a description used by dump.
205
- var debugDescription : String {
206
- return value. debugDescription
218
+ private var nonRootInfo : Info . NonRoot ? {
219
+ switch info {
220
+ case . root( _) : return nil
221
+ case . nonRoot( let info) : return info
222
+ }
207
223
}
208
224
209
- /// Prints the raw value of this node to the provided stream.
210
- /// - Parameter stream: The stream to which to print the raw tree.
211
- func write< Target> ( to target: inout Target )
212
- where Target: TextOutputStream {
213
- return value. write ( to: & target)
225
+ private var rootArena : SyntaxArena {
226
+ rootInfo. arena
214
227
}
215
- }
216
228
217
- /// SyntaxData is the underlying storage for each Syntax node.
218
- ///
219
- /// SyntaxData is an implementation detail, and should not be exposed to clients
220
- /// of SwiftSyntax.
221
- struct SyntaxData {
222
- private enum ParentOrArena {
223
- // For non-root nodes.
224
- case parent( SyntaxBox )
225
- // For root node.
226
- case arena( SyntaxArena )
227
- }
228
- private let parentOrArena : ParentOrArena
229
- private var arena : SyntaxArena {
230
- switch parentOrArena {
231
- case . arena( let arena) : return arena
232
- case . parent( let parentBox) : return parentBox. value. data. arena
229
+ private var root : SyntaxData {
230
+ switch info {
231
+ case . root( _) : return self
232
+ case . nonRoot( let info) : return info. parent. root
233
233
}
234
234
}
235
- var parent : Syntax ? {
236
- switch parentOrArena {
237
- case . parent( let parentBox) : return parentBox. value
238
- case . arena( _) : return nil
239
- }
235
+
236
+ var parent : SyntaxData ? {
237
+ nonRootInfo? . parent
240
238
}
241
- let absoluteRaw : AbsoluteRawSyntax
242
239
243
- var raw : RawSyntax { return absoluteRaw. raw }
240
+ var absoluteInfo : AbsoluteSyntaxInfo {
241
+ nonRootInfo? . absoluteInfo ?? . forRoot( raw)
242
+ }
244
243
245
- var indexInParent : Int { return Int ( absoluteRaw. info. indexInParent) }
244
+ var absoluteRaw : AbsoluteRawSyntax {
245
+ AbsoluteRawSyntax ( raw: raw, info: absoluteInfo)
246
+ }
246
247
247
- var nodeId : SyntaxIdentifier { return absoluteRaw. info. nodeId }
248
+ var indexInParent : Int {
249
+ Int ( absoluteInfo. indexInParent)
250
+ }
251
+
252
+ var nodeId : SyntaxIdentifier {
253
+ absoluteInfo. nodeId
254
+ }
248
255
249
256
/// The position of the start of this node's leading trivia
250
257
var position : AbsolutePosition {
251
- return absoluteRaw . position
258
+ AbsolutePosition ( utf8Offset : Int ( absoluteInfo . offset ) )
252
259
}
253
260
254
261
/// The position of the start of this node's content, skipping its trivia
@@ -263,26 +270,30 @@ struct SyntaxData {
263
270
264
271
/// The end position of this node, including its trivia.
265
272
var endPosition : AbsolutePosition {
266
- return absoluteRaw . endPosition
273
+ position + raw . totalLength
267
274
}
268
275
269
276
/// "designated" memberwise initializer of `SyntaxData`.
270
- private init ( _ absoluteRaw: AbsoluteRawSyntax , parentOrArena: ParentOrArena ) {
271
- self . parentOrArena = parentOrArena
272
- self . absoluteRaw = absoluteRaw
277
+ private init ( _ raw: RawSyntax , info: Info ) {
278
+ self . raw = raw
279
+ self . info = info
280
+ }
281
+
282
+ init ( _ raw: RawSyntax , parent: SyntaxData , absoluteInfo: AbsoluteSyntaxInfo ) {
283
+ self . init ( raw, info: . nonRoot( . init( parent: parent, absoluteInfo: absoluteInfo) ) )
273
284
}
274
285
275
286
/// Creates a `SyntaxData` with the provided raw syntax and parent.
276
287
/// - Parameters:
277
288
/// - absoluteRaw: The underlying `AbsoluteRawSyntax` of this node.
278
289
/// - parent: The parent of this node, or `nil` if this node is the root.
279
290
init ( _ absoluteRaw: AbsoluteRawSyntax , parent: Syntax ) {
280
- self . init ( absoluteRaw, parentOrArena : . parent( SyntaxBox ( parent ) ) )
291
+ self . init ( absoluteRaw. raw , parent : parent. data , absoluteInfo : absoluteRaw . info )
281
292
}
282
293
283
294
/// Creates a `SyntaxData` for a root raw node.
284
295
static func forRoot( _ raw: RawSyntax ) -> SyntaxData {
285
- SyntaxData ( . forRoot ( raw) , parentOrArena : . arena ( raw. arena) )
296
+ SyntaxData ( raw, info : . root ( . init ( arena : raw. arena) ) )
286
297
}
287
298
288
299
/// Returns the child data at the provided index in this data's layout.
@@ -300,7 +311,7 @@ struct SyntaxData {
300
311
var iter = RawSyntaxChildren ( absoluteRaw) . makeIterator ( )
301
312
for _ in 0 ..< index { _ = iter. next ( ) }
302
313
let ( raw, info) = iter. next ( ) !
303
- return SyntaxData ( AbsoluteRawSyntax ( raw: raw !, info : info ) , parent : parent )
314
+ return SyntaxData ( raw!, parent : self , absoluteInfo : info )
304
315
}
305
316
306
317
/// Creates a copy of `self` and recursively creates `SyntaxData` nodes up to
@@ -313,7 +324,7 @@ struct SyntaxData {
313
324
// If we have a parent already, then ask our current parent to copy itself
314
325
// recursively up to the root.
315
326
if let parent = parent {
316
- let parentData = parent. data . replacingChild ( newRaw, at: indexInParent)
327
+ let parentData = parent. replacingChild ( newRaw, at: indexInParent)
317
328
let newParent = Syntax ( parentData)
318
329
return SyntaxData ( absoluteRaw. replacingSelf ( newRaw, newRootId: parentData. nodeId. rootId) , parent: newParent)
319
330
} else {
0 commit comments