blob: a965149ebc8c5cf94d4aee60bea654b146678f81 [file] [log] [blame]
/*
* Copyright 2014-present Facebook, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License"); you may
* not use this file except in compliance with the License. You may obtain
* a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*/
package com.facebook.buck.apple;
import com.dd.plist.NSDictionary;
import com.dd.plist.PropertyListParser;
import com.facebook.buck.log.Logger;
import com.google.common.collect.ImmutableMap;
import java.io.BufferedInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.nio.file.DirectoryStream;
import java.nio.file.Files;
import java.nio.file.NoSuchFileException;
import java.nio.file.Path;
/**
* Utility class to discover the location of toolchains contained inside an Xcode
* installation.
*/
public class AppleToolchainDiscovery {
private static final Logger LOG = Logger.get(AppleToolchainDiscovery.class);
// Utility class; do not instantiate.
private AppleToolchainDiscovery() { }
/**
* Given a path to an Xcode developer directory, walks through the
* toolchains and builds a map of (identifier: path) pairs of the
* toolchains inside.
*/
public static ImmutableMap<String, Path> discoverAppleToolchainPaths(Path xcodeDir)
throws IOException {
LOG.debug("Searching for Xcode toolchains under %s", xcodeDir);
ImmutableMap.Builder<String, Path> toolchainIdentifiersToPathsBuilder = ImmutableMap.builder();
Path toolchains = xcodeDir.resolve("Toolchains");
if (!Files.exists(toolchains)) {
return toolchainIdentifiersToPathsBuilder.build();
}
try (DirectoryStream<Path> toolchainStream = Files.newDirectoryStream(
toolchains,
"*.xctoolchain")) {
for (Path toolchainDir : toolchainStream) {
LOG.debug("Getting identifier for for Xcode toolchain under %s", toolchainDir);
addIdentiferForToolchain(toolchainDir, toolchainIdentifiersToPathsBuilder);
}
}
return toolchainIdentifiersToPathsBuilder.build();
}
private static void addIdentiferForToolchain(
Path toolchainDir,
ImmutableMap.Builder<String, Path> toolchainBuilder) throws IOException {
try (InputStream toolchainInfoPlist = Files.newInputStream(
toolchainDir.resolve("ToolchainInfo.plist"));
BufferedInputStream bufferedToolchainInfoPlist = new BufferedInputStream(
toolchainInfoPlist)) {
NSDictionary parsedToolchainInfoPlist;
try {
parsedToolchainInfoPlist = (NSDictionary) PropertyListParser.parse(
bufferedToolchainInfoPlist);
} catch (Exception e) {
throw new IOException(e);
}
String identifier = parsedToolchainInfoPlist.objectForKey("Identifier")
.toString();
LOG.debug("Mapped SDK identifier %s to path %s", identifier, toolchainDir);
toolchainBuilder.put(identifier, toolchainDir);
} catch (FileNotFoundException | NoSuchFileException e) {
LOG.error(e, "No ToolchainInfo.plist found under toolchain path %s, ignoring", toolchainDir);
}
}
}