Merge remote-tracking branch 'origin/master' into swift-4.0-branch
diff --git a/Foundation/NSURL.swift b/Foundation/NSURL.swift
index 9f06158..06a5217 100644
--- a/Foundation/NSURL.swift
+++ b/Foundation/NSURL.swift
@@ -405,7 +405,7 @@
         let buffer = malloc(bytesNeeded)!.bindMemory(to: UInt8.self, capacity: bytesNeeded)
         let bytesFilled = CFURLGetBytes(_cfObject, buffer, bytesNeeded)
         if bytesFilled == bytesNeeded {
-            return Data(bytesNoCopy: buffer, count: bytesNeeded, deallocator: .none)
+            return Data(bytesNoCopy: buffer, count: bytesNeeded, deallocator: .free)
         } else {
             fatalError()
         }
diff --git a/TestFoundation/TestURL.swift b/TestFoundation/TestURL.swift
index b0977b1..1ce0bf9 100644
--- a/TestFoundation/TestURL.swift
+++ b/TestFoundation/TestURL.swift
@@ -64,6 +64,7 @@
             ("test_reachable", test_reachable),
             ("test_copy", test_copy),
             ("test_itemNSCoding", test_itemNSCoding),
+            ("test_dataRepresentation", test_dataRepresentation),
         ]
     }
     
@@ -491,6 +492,13 @@
         let queryItemB = NSKeyedUnarchiver.unarchiveObject(with: NSKeyedArchiver.archivedData(withRootObject: queryItemA)) as! NSURLQueryItem
         XCTAssertEqual(queryItemA, queryItemB, "Archived then unarchived query item must be equal.")
     }
+
+    func test_dataRepresentation() {
+        let url = NSURL(fileURLWithPath: "/tmp/foo")
+        let url2 = NSURL(dataRepresentation: url.dataRepresentation,
+            relativeTo: nil)
+        XCTAssertEqual(url, url2)
+    }
 }
     
 class TestURLComponents : XCTestCase {
diff --git a/build.py b/build.py
index 7cca01a..00d8588 100755
--- a/build.py
+++ b/build.py
@@ -15,8 +15,8 @@
 
 swift_cflags = ['-DDEPLOYMENT_RUNTIME_SWIFT']
 if Configuration.current.target.sdk == OSType.Linux:
-	foundation.CFLAGS = '`${PKG_CONFIG} icu-uc icu-i18n --cflags-only-I` -DDEPLOYMENT_TARGET_LINUX -D_GNU_SOURCE -DCF_CHARACTERSET_DATA_DIR="CoreFoundation/CharacterSets"'
-	foundation.LDFLAGS = '${SWIFT_USE_LINKER} -Wl,@./CoreFoundation/linux.ld -lswiftGlibc `${PKG_CONFIG} icu-uc icu-i18n --libs` -Wl,-Bsymbolic '
+	foundation.CFLAGS = '-DDEPLOYMENT_TARGET_LINUX -D_GNU_SOURCE -DCF_CHARACTERSET_DATA_DIR="CoreFoundation/CharacterSets"'
+	foundation.LDFLAGS = '${SWIFT_USE_LINKER} -Wl,@./CoreFoundation/linux.ld -lswiftGlibc -Wl,-Bsymbolic '
 	Configuration.current.requires_pkg_config = True
 elif Configuration.current.target.sdk == OSType.FreeBSD:
 	foundation.CFLAGS = '-DDEPLOYMENT_TARGET_FREEBSD -I/usr/local/include -I/usr/local/include/libxml2 -I/usr/local/include/curl '
@@ -61,35 +61,55 @@
 	'-Wno-unused-variable',
 	'-Wno-int-conversion',
 	'-Wno-unused-function',
-	'-I${SYSROOT}/usr/include/libxml2',
-	'-I${SYSROOT}/usr/include/curl',
 	'-I./',
 ])
 
 swift_cflags += [
 	'-I${BUILD_DIR}/Foundation/usr/lib/swift',
-	'-I${SYSROOT}/usr/include/libxml2',
-	'-I${SYSROOT}/usr/include/curl'
 ]
 
 if "XCTEST_BUILD_DIR" in Configuration.current.variables:
 	swift_cflags += [
 		'-I${XCTEST_BUILD_DIR}',
 		'-L${XCTEST_BUILD_DIR}',
-		'-I${SYSROOT}/usr/include/libxml2',
-		'-I${SYSROOT}/usr/include/curl'
 	]
 
-triple = Configuration.current.target.triple
-if triple.find("linux") != -1:
-	foundation.LDFLAGS += '-lcurl '
+if Configuration.current.requires_pkg_config:
+    pkg_config_dependencies = [
+        'icu-i18n',
+        'icu-uc',
+        'libcurl',
+        'libxml-2.0',
+    ]
+    for package_name in pkg_config_dependencies:
+        try:
+            package = PkgConfig(package_name)
+        except PkgConfig.Error as e:
+            sys.exit("pkg-config error for package {}: {}".format(package_name, e))
+        foundation.CFLAGS += ' {} '.format(' '.join(package.cflags))
+        foundation.LDFLAGS += ' {} '.format(' '.join(package.ldflags))
+        swift_cflags += package.swiftc_flags
+else:
+	foundation.CFLAGS += ''.join([
+		'-I${SYSROOT}/usr/include/curl ',
+		'-I${SYSROOT}/usr/include/libxml2 ',
+	])
+	foundation.LDFLAGS += ''.join([
+		'-lcurl ',
+		'-lxml2 ',
+	])
+	swift_cflags += ''.join([
+		'-I${SYSROOT}/usr/include/curl ',
+		'-I${SYSROOT}/usr/include/libxml2 ',
+	])
 
+triple = Configuration.current.target.triple
 if triple == "armv7-none-linux-androideabi":
 	foundation.LDFLAGS += '-llog '
 else:
 	foundation.LDFLAGS += '-lpthread '
 
-foundation.LDFLAGS += '-ldl -lm -lswiftCore -lxml2 '
+foundation.LDFLAGS += '-ldl -lm -lswiftCore '
 
 # Configure use of Dispatch in CoreFoundation and Foundation if libdispatch is being built
 if "LIBDISPATCH_SOURCE_DIR" in Configuration.current.variables:
diff --git a/configure b/configure
index 4e0f128..f4cc022 100755
--- a/configure
+++ b/configure
@@ -32,6 +32,8 @@
 from lib.product import Application
 from lib.product import Executable
 
+from lib.pkg_config import PkgConfig
+
 from lib.script import Script
 
 from lib.target import ArchSubType
diff --git a/lib/__init__.py b/lib/__init__.py
index 158123d..b55f8a5 100644
--- a/lib/__init__.py
+++ b/lib/__init__.py
@@ -11,8 +11,9 @@
     "config",
     "path",
     "phases",
+    "pkg_config",
     "product",
     "script",
     "target",
     "workspace",
-]
\ No newline at end of file
+]
diff --git a/lib/pkg_config.py b/lib/pkg_config.py
new file mode 100644
index 0000000..e511075
--- /dev/null
+++ b/lib/pkg_config.py
@@ -0,0 +1,65 @@
+from __future__ import print_function
+
+import shlex
+import subprocess
+import sys
+
+from .config import Configuration
+
+
+class PkgConfig(object):
+    class Error(Exception):
+        """Raised when information could not be obtained from pkg-config."""
+
+    def __init__(self, package_name):
+        """Query pkg-config for information about a package.
+
+        :type package_name: str
+        :param package_name: The name of the package to query.
+        :raises PkgConfig.Error: When a call to pkg-config fails.
+        """
+        self.package_name = package_name
+        self._cflags = self._call("--cflags")
+        self._cflags_only_I = self._call("--cflags-only-I")
+        self._cflags_only_other = self._call("--cflags-only-other")
+        self._libs = self._call("--libs")
+        self._libs_only_l = self._call("--libs-only-l")
+        self._libs_only_L = self._call("--libs-only-L")
+        self._libs_only_other = self._call("--libs-only-other")
+
+    def _call(self, *pkg_config_args):
+        try:
+            cmd = [Configuration.current.pkg_config] + list(pkg_config_args) + [self.package_name]
+            print("Executing command '{}'".format(cmd), file=sys.stderr)
+            return shlex.split(subprocess.check_output(cmd))
+        except subprocess.CalledProcessError as e:
+            raise self.Error("pkg-config exited with error code {}".format(e.returncode))
+
+    @property
+    def swiftc_flags(self):
+        """Flags for this package in a format suitable for passing to `swiftc`.
+
+        :rtype: list[str]
+        """
+        return (
+                ["-Xcc {}".format(s) for s in self._cflags_only_other]
+                + ["-Xlinker {}".format(s) for s in self._libs_only_other]
+                + self._cflags_only_I
+                + self._libs_only_L
+                + self._libs_only_l)
+
+    @property
+    def cflags(self):
+        """CFLAGS for this package.
+
+        :rtype: list[str]
+        """
+        return self._cflags
+
+    @property
+    def ldflags(self):
+        """LDFLAGS for this package.
+
+        :rtype: list[str]
+        """
+        return self._libs