diff --git a/Sources/protoc-gen-swift/OneofGenerator.swift b/Sources/protoc-gen-swift/OneofGenerator.swift index 0a025c96b..836045942 100644 --- a/Sources/protoc-gen-swift/OneofGenerator.swift +++ b/Sources/protoc-gen-swift/OneofGenerator.swift @@ -219,9 +219,21 @@ class OneofGenerator { p.print( "\(visibility)static func ==(lhs: \(swiftFullName), rhs: \(swiftFullName)) -> Bool {\n") p.indent() - p.print("switch (lhs, rhs) {\n") + p.print( + "// The use of inline closures is to circumvent an issue where the compiler\n", + "// allocates stack space for every case branch when no optimizations are\n", + "// enabled. https://github.com/apple/swift-protobuf/issues/1034\n", + "switch (lhs, rhs) {\n") for f in fields { - p.print("case (\(f.dottedSwiftName)(let l), \(f.dottedSwiftName)(let r)): return l == r\n") + p.print( + "case (\(f.dottedSwiftName), \(f.dottedSwiftName)): return {\n") + p.indent() + p.print( + "guard case \(f.dottedSwiftName)(let l) = lhs, case \(f.dottedSwiftName)(let r) = rhs else { preconditionFailure() }\n", + "return l == r\n") + p.outdent() + p.print( + "}()\n") } if fields.count > 1 { // A tricky edge case: If the oneof only has a single case, then