Skip to content

Commit 08857cd

Browse files
committed
[tibs] Consolidate uses of Process and fix warnings
Fix warnings by using the non-deprecated APIs, and while we're at it consolidate all the uses into a single place that checks the result and collects stdout. Inspired by SwiftPM's checkNonZeroExit.
1 parent 7cf04b8 commit 08857cd

File tree

3 files changed

+74
-82
lines changed

3 files changed

+74
-82
lines changed

Sources/ISDBTibs/Process.swift

Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
//===----------------------------------------------------------------------===//
2+
//
3+
// This source file is part of the Swift.org open source project
4+
//
5+
// Copyright (c) 2014 - 2019 Apple Inc. and the Swift project authors
6+
// Licensed under Apache License v2.0 with Runtime Library Exception
7+
//
8+
// See https://swift.org/LICENSE.txt for license information
9+
// See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
10+
//
11+
//===----------------------------------------------------------------------===//
12+
13+
import Foundation
14+
15+
extension Process {
16+
17+
enum TibsProcessError: Error {
18+
case nonZeroExit(TerminationReason, Int32)
19+
case invalidUTF8Output(Data)
20+
}
21+
22+
/// Runs a subprocess and returns its output as a String if it has a zero exit.
23+
static func tibs_checkNonZeroExit(
24+
arguments: [String],
25+
environment: [String: String]? = nil
26+
) throws -> String {
27+
let p = Process()
28+
let out = Pipe()
29+
30+
if #available(macOS 10.13, *) {
31+
p.executableURL = URL(fileURLWithPath: arguments[0], isDirectory: false)
32+
} else {
33+
p.launchPath = arguments[0]
34+
}
35+
36+
p.arguments = Array(arguments[1...])
37+
if let environment = environment {
38+
p.environment = environment
39+
}
40+
p.standardOutput = out
41+
42+
if #available(macOS 10.13, *) {
43+
try p.run()
44+
} else {
45+
p.launch()
46+
}
47+
48+
p.waitUntilExit()
49+
50+
if p.terminationReason != .exit || p.terminationStatus != 0 {
51+
throw TibsProcessError.nonZeroExit(p.terminationReason, p.terminationStatus)
52+
}
53+
54+
let data = out.fileHandleForReading.readDataToEndOfFile()
55+
guard let str = String(data: data, encoding: .utf8) else {
56+
throw TibsProcessError.invalidUTF8Output(data)
57+
}
58+
return str
59+
}
60+
}

Sources/ISDBTibs/TibsBuilder.swift

Lines changed: 8 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -118,19 +118,7 @@ extension TibsBuilder {
118118

119119
/// *For Testing* Build and collect a list of commands that were (re)built.
120120
public func _buildTest() throws -> Set<String> {
121-
let pipe = Pipe()
122-
123-
do {
124-
try buildImpl { process in
125-
process.standardOutput = pipe
126-
}
127-
} catch TibsBuilder.Error.buildFailure(let tc, let ts) {
128-
let out = String(data: pipe.fileHandleForReading.readDataToEndOfFile(), encoding: .utf8)!
129-
print(out)
130-
throw TibsBuilder.Error.buildFailure(tc, exitCode: ts)
131-
}
132-
133-
let out = String(data: pipe.fileHandleForReading.readDataToEndOfFile(), encoding: .utf8)!
121+
let out = try buildImpl()
134122
var rest = out.startIndex..<out.endIndex
135123

136124
var result = Set<String>()
@@ -144,21 +132,16 @@ extension TibsBuilder {
144132
return result
145133
}
146134

147-
func buildImpl(processCustomization: (Process) -> () = { _ in }) throws {
135+
@discardableResult
136+
func buildImpl() throws -> String {
148137
guard let ninja = toolchain.ninja?.path else {
149138
throw Error.noNinjaBinaryConfigured
150139
}
151140

152-
let p = Process()
153-
p.launchPath = ninja
154-
p.arguments = ["-C", buildRoot.path]
155-
156-
processCustomization(p)
157-
158-
p.launch()
159-
p.waitUntilExit()
160-
if p.terminationReason != .exit || p.terminationStatus != 0 {
161-
throw Error.buildFailure(p.terminationReason, exitCode: p.terminationStatus)
141+
do {
142+
return try Process.tibs_checkNonZeroExit(arguments: [ninja, "-C", buildRoot.path])
143+
} catch Process.TibsProcessError.nonZeroExit(let reason, let code) {
144+
throw Error.buildFailure(reason, exitCode: code)
162145
}
163146
}
164147
}
@@ -367,24 +350,7 @@ extension TibsBuilder {
367350
}
368351

369352
func xcrunSDKPath() -> String {
370-
let p = Process()
371-
p.launchPath = "/usr/bin/xcrun"
372-
p.arguments = ["--show-sdk-path"]
373-
374-
let out = Pipe()
375-
p.standardOutput = out
376-
377-
p.launch()
378-
p.waitUntilExit()
379-
380-
if p.terminationReason != .exit || p.terminationStatus != 0 {
381-
fatalError("unexpected non-zero exit \(p.terminationStatus) from xcrun --show-sdkpath")
382-
}
383-
384-
let data = out.fileHandleForReading.readDataToEndOfFile()
385-
guard var path = String(data: data, encoding: .utf8) else {
386-
fatalError("invalid output \(data) from xcrun --show-sdkpath")
387-
}
353+
var path = try! Process.tibs_checkNonZeroExit(arguments: ["/usr/bin/xcrun", "--show-sdk-path"])
388354
if path.last == "\n" {
389355
path = String(path.dropLast())
390356
}

Sources/ISDBTibs/TibsToolchain.swift

Lines changed: 6 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -40,17 +40,7 @@ public final class TibsToolchain {
4040
#endif
4141

4242
public private(set) lazy var clangVersionOutput: String = {
43-
let p = Process()
44-
p.launchPath = clang.path
45-
p.arguments = ["--version"]
46-
let pipe = Pipe()
47-
p.standardOutput = pipe
48-
p.launch()
49-
p.waitUntilExit()
50-
guard p.terminationReason == .exit && p.terminationStatus == 0 else {
51-
fatalError("could not get clang --version")
52-
}
53-
return String(data: pipe.fileHandleForReading.readDataToEndOfFile(), encoding: .utf8)!
43+
return try! Process.tibs_checkNonZeroExit(arguments: [clang.path, "--version"])
5444
}()
5545

5646
public private(set) lazy var clangHasIndexSupport: Bool = {
@@ -59,18 +49,7 @@ public final class TibsToolchain {
5949

6050
public private(set) lazy var ninjaVersion: (Int, Int, Int) = {
6151
precondition(ninja != nil, "expected non-nil ninja in ninjaVersion")
62-
let p = Process()
63-
p.launchPath = ninja!.path
64-
p.arguments = ["--version"]
65-
let pipe = Pipe()
66-
p.standardOutput = pipe
67-
p.launch()
68-
p.waitUntilExit()
69-
guard p.terminationReason == .exit && p.terminationStatus == 0 else {
70-
fatalError("could not get ninja --version")
71-
}
72-
73-
var out = String(data: pipe.fileHandleForReading.readDataToEndOfFile(), encoding: .utf8)!
52+
var out = try! Process.tibs_checkNonZeroExit(arguments: [ninja!.path, "--version"])
7453
out = out.trimmingCharacters(in: .whitespacesAndNewlines)
7554
let components = out.split(separator: ".", maxSplits: 3)
7655
guard let maj = Int(String(components[0])),
@@ -179,30 +158,17 @@ extension TibsToolchain {
179158

180159
/// Returns the path to the given tool, as found by `xcrun --find` on macOS, or `which` on Linux.
181160
public func findTool(name: String) -> URL? {
182-
let p = Process()
183161
#if os(macOS)
184-
p.launchPath = "/usr/bin/xcrun"
185-
p.arguments = ["--find", name]
162+
let cmd = ["/usr/bin/xcrun", "--find", name]
186163
#else
187-
p.launchPath = "/usr/bin/which"
188-
p.arguments = [name]
164+
let cmd = ["/usr/bin/which", name]
189165
#endif
190-
let out = Pipe()
191-
p.standardOutput = out
192-
193-
p.launch()
194-
p.waitUntilExit()
195-
196-
if p.terminationReason != .exit || p.terminationStatus != 0 {
197-
return nil
198-
}
199166

200-
let data = out.fileHandleForReading.readDataToEndOfFile()
201-
guard var path = String(data: data, encoding: .utf8) else {
167+
guard var path = try? Process.tibs_checkNonZeroExit(arguments: cmd) else {
202168
return nil
203169
}
204170
if path.last == "\n" {
205171
path = String(path.dropLast())
206172
}
207-
return URL(fileURLWithPath: path)
173+
return URL(fileURLWithPath: path, isDirectory: false)
208174
}

0 commit comments

Comments
 (0)