//===----------------------------------------------------------------------===//
// This source file is part of the Swift.org open source project
//
// Copyright (c) 2014 - 2017 Apple Inc. and the Swift project authors
// Licensed under Apache License v2.0 with Runtime Library Exception
//
// See https://swift.org/LICENSE.txt for license information
// See https://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
//
//===----------------------------------------------------------------------===//

const char *usage = 
    "  swift-stdlib-tool --print [options...]\n"
    "    Find and print the Swift libraries required by an app.\n"
    "\n"
    "  swift-stdlib-tool --copy [options...]\n"
    "    Copy the Swift libraries into an app bundle, and optionally sign them.\n"
    "\n"
    "  --verbose\n"
    "      Print progress.\n"
    "  --verbose --verbose\n"
    "      Print debugging details.\n"
    "  --help\n"
    "      Print usage.\n"
    "\n"
    "  Options for lookup:\n"
    "  --scan-executable <path>\n"
    "      Scan the executable at <path> for references to Swift libraries.\n"
    "      This option may be set multiple times.\n"
    "  --scan-folder <path>\n"
    "      Scan any executables inside <path> for references to Swift libraries.\n"
    "      This option may be set multiple times.\n"
    "  --platform <macosx|iphoneos|iphonesimulator>\n"
    "      Use the Swift libraries for <platform>.\n"
    "  --source-libraries <path>\n"
    "      Search <path> for Swift libraries.\n"
    "      The default is /path/to/swift-stdlib-tool/../../lib/swift/<platform>/\n"
    "\n"
    "  Options for copying and signing:\n"
    "  --destination <path>\n"
    "      Copy Swift libraries into <path>.\n"
    "  --unsigned-destination <path>\n"
    "      Copy Swift libraries into <path> without signing them.\n"
    "  --sign <identity>\n"
    "      Sign copied Swift libraries using <identity>.\n"
    "  --keychain <keychain>\n"
    "      Search <keychain> for the code signing identity.\n"
    "  --Xcodesign <option>\n"
    "      Pass <option> to the codesign tool.\n"
    "  --strip-bitcode\n"
    "      Remove embedded bitcode from libraries copied to --destination.\n"
    "      Libraries copied to --unsigned-destination are unmodified.\n"
    "\n"
    "  Options for libraries copied as resources\n"
    "  --resource-library <library>\n"
    "      Copy <library> and its dependencies as resources without signing\n"
    "      them. These copies are in addition to any libraries copied as a result\n"
    "      of the --scan-executable option.\n"
    "      Any library in the Swift library search path can be specified for\n"
    "      <library>.\n"
    "      This option may be set multiple times.\n"
    "  --resource-destination <path>\n"
    "      The <path> to copy Swift resource libraries to.\n"
    "\n"
    ;

#include <sys/types.h>
#include <sys/uio.h>
#include <sys/stat.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <errno.h>
#include <fcntl.h>
#include <os/overflow.h>
#include <mach-o/fat.h>
#include <mach-o/dyld.h>
#include <mach-o/loader.h>
#include <libkern/OSByteOrder.h>

#include <algorithm>
using namespace std;

#include <Foundation/Foundation.h>

#pragma clang diagnostic ignored "-Wgcc-compat"

#ifndef CPU_TYPE_ARM64
#   define CPU_TYPE_ARM64  ((cpu_type_t) (CPU_TYPE_ARM | CPU_ARCH_ABI64))
#endif

static int Verbose = 0;

#ifdef __OPTIMIZE__
#define INLINE	__attribute__((always_inline))
#else
#define INLINE
#endif

//
// This abstraction layer is for use with file formats that have 64-bit/32-bit and Big-Endian/Little-Endian variants
//
// For example: to make a utility that handles 32-bit little enidan files use:  Pointer32<LittleEndian>
//
//
//		get16()			read a 16-bit number from an E endian struct
//		set16()			write a 16-bit number to an E endian struct
//		get32()			read a 32-bit number from an E endian struct
//		set32()			write a 32-bit number to an E endian struct
//		get64()			read a 64-bit number from an E endian struct
//		set64()			write a 64-bit number to an E endian struct
//
//		getBits()		read a bit field from an E endian struct (bitCount=number of bits in field, firstBit=bit index of field)
//		setBits()		write a bit field to an E endian struct (bitCount=number of bits in field, firstBit=bit index of field)
//
//		getBitsRaw()	read a bit field from a struct with native endianness
//		setBitsRaw()	write a bit field from a struct with native endianness
//

class BigEndian
{
public:
	static uint16_t	get16(const uint16_t& from)				INLINE { return OSReadBigInt16(&from, 0); }
	static void		set16(uint16_t& into, uint16_t value)	INLINE { OSWriteBigInt16(&into, 0, value); }
	
	static uint32_t	get32(const uint32_t& from)				INLINE { return OSReadBigInt32(&from, 0); }
	static void		set32(uint32_t& into, uint32_t value)	INLINE { OSWriteBigInt32(&into, 0, value); }
	
	static uint64_t get64(const uint64_t& from)				INLINE { return OSReadBigInt64(&from, 0); }
	static void		set64(uint64_t& into, uint64_t value)	INLINE { OSWriteBigInt64(&into, 0, value); }
	
	static uint32_t	getBits(const uint32_t& from, 
						uint8_t firstBit, uint8_t bitCount)	INLINE { return getBitsRaw(get32(from), firstBit, bitCount); }
	static void		setBits(uint32_t& into, uint32_t value,
						uint8_t firstBit, uint8_t bitCount)	INLINE { uint32_t temp = get32(into); setBitsRaw(temp, value, firstBit, bitCount); set32(into, temp); }

	static uint32_t	getBitsRaw(const uint32_t& from, 
						uint8_t firstBit, uint8_t bitCount)	INLINE { return ((from >> (32-firstBit-bitCount)) & ((1<<bitCount)-1)); }
	static void		setBitsRaw(uint32_t& into, uint32_t value,
						uint8_t firstBit, uint8_t bitCount)	INLINE { uint32_t temp = into; 
																							const uint32_t mask = ((1<<bitCount)-1); 
																							temp &= ~(mask << (32-firstBit-bitCount)); 
																							temp |= ((value & mask) << (32-firstBit-bitCount)); 
																							into = temp; }
	enum { little_endian = 0 };
};


class LittleEndian
{
public:
	static uint16_t	get16(const uint16_t& from)				INLINE { return OSReadLittleInt16(&from, 0); }
	static void		set16(uint16_t& into, uint16_t value)	INLINE { OSWriteLittleInt16(&into, 0, value); }
	
	static uint32_t	get32(const uint32_t& from)				INLINE { return OSReadLittleInt32(&from, 0); }
	static void		set32(uint32_t& into, uint32_t value)	INLINE { OSWriteLittleInt32(&into, 0, value); }
	
	static uint64_t get64(const uint64_t& from)				INLINE { return OSReadLittleInt64(&from, 0); }
	static void		set64(uint64_t& into, uint64_t value)	INLINE { OSWriteLittleInt64(&into, 0, value); }

	static uint32_t	getBits(const uint32_t& from,
						uint8_t firstBit, uint8_t bitCount)	INLINE { return getBitsRaw(get32(from), firstBit, bitCount); }
	static void		setBits(uint32_t& into, uint32_t value,
						uint8_t firstBit, uint8_t bitCount)	INLINE { uint32_t temp = get32(into); setBitsRaw(temp, value, firstBit, bitCount); set32(into, temp); }

	static uint32_t	getBitsRaw(const uint32_t& from,
						uint8_t firstBit, uint8_t bitCount)	INLINE { return ((from >> firstBit) & ((1<<bitCount)-1)); }
	static void		setBitsRaw(uint32_t& into, uint32_t value,
						uint8_t firstBit, uint8_t bitCount)	INLINE {  uint32_t temp = into; 
																							const uint32_t mask = ((1<<bitCount)-1); 
																							temp &= ~(mask << firstBit); 
																							temp |= ((value & mask) << firstBit); 
																							into = temp; }
	enum { little_endian = 1 };
};

#if __BIG_ENDIAN__
typedef BigEndian CurrentEndian;
typedef LittleEndian OtherEndian;
#elif __LITTLE_ENDIAN__
typedef LittleEndian CurrentEndian;
typedef BigEndian OtherEndian;
#else
#error unknown endianness
#endif


template <typename _E>
class Pointer32
{
public:
	typedef uint32_t	uint_t;
	typedef int32_t		sint_t;
	typedef _E			E;
	
	static uint64_t	getP(const uint_t& from)				INLINE { return _E::get32(from); }
	static void		setP(uint_t& into, uint64_t value)		INLINE { _E::set32(into, value); }
};


template <typename _E>
class Pointer64
{
public:
	typedef uint64_t	uint_t;
	typedef int64_t		sint_t;
	typedef _E			E;
	
	static uint64_t	getP(const uint_t& from)				INLINE { return _E::get64(from); }
	static void		setP(uint_t& into, uint64_t value)		INLINE { _E::set64(into, value); }
};


//
// mach-o file header
//
template <typename P> struct macho_header_content {};
template <> struct macho_header_content<Pointer32<BigEndian> >    { mach_header		fields; };
template <> struct macho_header_content<Pointer64<BigEndian> >	  { mach_header_64	fields; };
template <> struct macho_header_content<Pointer32<LittleEndian> > { mach_header		fields; };
template <> struct macho_header_content<Pointer64<LittleEndian> > { mach_header_64	fields; };

template <typename P>
class macho_header {
public:
	uint32_t		magic() const					INLINE { return E::get32(header.fields.magic); }
	void			set_magic(uint32_t value)		INLINE { E::set32(header.fields.magic, value); }

	uint32_t		cputype() const					INLINE { return E::get32(header.fields.cputype); }
	void			set_cputype(uint32_t value)		INLINE { E::set32((uint32_t&)header.fields.cputype, value); }

	uint32_t		cpusubtype() const				INLINE { return E::get32(header.fields.cpusubtype); }
	void			set_cpusubtype(uint32_t value)	INLINE { E::set32((uint32_t&)header.fields.cpusubtype, value); }

	uint32_t		filetype() const				INLINE { return E::get32(header.fields.filetype); }
	void			set_filetype(uint32_t value)	INLINE { E::set32(header.fields.filetype, value); }

	uint32_t		ncmds() const					INLINE { return E::get32(header.fields.ncmds); }
	void			set_ncmds(uint32_t value)		INLINE { E::set32(header.fields.ncmds, value); }

	uint32_t		sizeofcmds() const				INLINE { return E::get32(header.fields.sizeofcmds); }
	void			set_sizeofcmds(uint32_t value)	INLINE { E::set32(header.fields.sizeofcmds, value); }

	uint32_t		flags() const					INLINE { return E::get32(header.fields.flags); }
	void			set_flags(uint32_t value)		INLINE { E::set32(header.fields.flags, value); }

	uint32_t		reserved() const				INLINE { return E::get32(header.fields.reserved); }
	void			set_reserved(uint32_t value)	INLINE { E::set32(header.fields.reserved, value); }

	typedef typename P::E		E;
private:
	macho_header_content<P>	header;
};


//
// mach-o load command
//
template <typename P>
class macho_load_command {
public:
	uint32_t		cmd() const						INLINE { return E::get32(command.cmd); }
	void			set_cmd(uint32_t value)			INLINE { E::set32(command.cmd, value); }

	uint32_t		cmdsize() const					INLINE { return E::get32(command.cmdsize); }
	void			set_cmdsize(uint32_t value)		INLINE { E::set32(command.cmdsize, value); }

	typedef typename P::E		E;
private:
	load_command	command;
};


//
// mach-o uuid load command
//
template <typename P>
class macho_uuid_command {
public:
	uint32_t		cmd() const								INLINE { return E::get32(fields.cmd); }
	void			set_cmd(uint32_t value)					INLINE { E::set32(fields.cmd, value); }

	uint32_t		cmdsize() const							INLINE { return E::get32(fields.cmdsize); }
	void			set_cmdsize(uint32_t value)				INLINE { E::set32(fields.cmdsize, value); }

	const uint8_t*	uuid() const							INLINE { return fields.uuid; }
	void			set_uuid(uint8_t value[16])				INLINE { memcpy(&fields.uuid, value, 16); }
			
	typedef typename P::E		E;
private:
	uuid_command	fields;
};


//
// mach-o dylib load command
//
template <typename P>
class macho_dylib_command {
public:
	uint32_t		cmd() const									INLINE { return E::get32(fields.cmd); }
	void			set_cmd(uint32_t value)						INLINE { E::set32(fields.cmd, value); }

	uint32_t		cmdsize() const								INLINE { return E::get32(fields.cmdsize); }
	void			set_cmdsize(uint32_t value)					INLINE { E::set32(fields.cmdsize, value); }

	uint32_t		name_offset() const							INLINE { return E::get32(fields.dylib.name.offset); }
	void			set_name_offset(uint32_t value)				INLINE { E::set32(fields.dylib.name.offset, value);  }
	
	uint32_t		timestamp() const							INLINE { return E::get32(fields.dylib.timestamp); }
	void			set_timestamp(uint32_t value)				INLINE { E::set32(fields.dylib.timestamp, value); }

	uint32_t		current_version() const						INLINE { return E::get32(fields.dylib.current_version); }
	void			set_current_version(uint32_t value)			INLINE { E::set32(fields.dylib.current_version, value); }

	uint32_t		compatibility_version() const				INLINE { return E::get32(fields.dylib.compatibility_version); }
	void			set_compatibility_version(uint32_t value)	INLINE { E::set32(fields.dylib.compatibility_version, value); }

	const char*		name() const								INLINE { return (const char*)&fields + name_offset(); }
	void			set_name_offset()							INLINE { set_name_offset(sizeof(fields)); }
	
	typedef typename P::E		E;
private:
	dylib_command	fields;
};


// Print everything to standard output.
// Mixing stdout and stderr looks bad when the output is reprinted by Xcode.

void printUsage() 
{
    fprintf(stdout, "%s", usage);
}

void fail(const char *msg, ...) 
    __attribute__((format(printf, 1, 2))) __attribute__((noreturn))
{
    va_list args;
    va_start(args, msg);
    char *msg2;
    asprintf(&msg2, "*** error: %s\n", msg);
    vfprintf(stdout, msg2, args);
    exit(1);
}

void fail_errno(const char *msg, ...) 
    __attribute__((format(printf, 1, 2))) __attribute__((noreturn))
{
    va_list args;
    va_start(args, msg);
    char *msg2;
    asprintf(&msg2, "*** error: %s: %s\n", msg, strerror(errno));
    vfprintf(stdout, msg2, args);
    exit(1);
}

void fail_usage(const char *msg, ...) 
    __attribute__((format(printf, 1, 2))) __attribute__((noreturn))
{
    va_list args;
    va_start(args, msg);
    char *msg2;
    asprintf(&msg2, "*** error: %s\n\n", msg);
    vfprintf(stdout, msg2, args);
    printUsage();
    exit(1);
}


void log_vn(int verbosity, const char *msg, va_list args)
    __attribute__((format(printf, 2, 0)))
{
    if (verbosity <= Verbose) {
        char *msg2;
        asprintf(&msg2, "%s\n", msg);
        vfprintf(stdout, msg2, args);
        free(msg2);
    }
}

int log_v(const char *msg, ...) 
    __attribute__((format(printf, 1, 2)))
{
    va_list args;
    va_start(args, msg);
    log_vn(1, msg, args);
    return -1;
}

int log_vv(const char *msg, ...) 
    __attribute__((format(printf, 1, 2)))
{
    va_list args;
    va_start(args, msg);
    log_vn(2, msg, args);
    return -1;
}


ssize_t pread_all(int fd, void *buf, size_t count, off_t offset)
{
    size_t total = 0;
    while (total < count) {
        ssize_t readed = pread(fd, (void *)((char *)buf+total), 
                               count-total, offset+total);
        if (readed > 0) total += readed;     // got data
        else if (readed == 0) return total;  // EOF: done
        else if (readed == -1  &&  errno != EINTR) return -1;  
                                                   // error but not EINTR: fail
    }

    return total;
}


template <typename T> 
int parse_macho(int fd, uint32_t offset, uint32_t size, 
                void (^dylibVisitor)(NSString *path), 
                void (^uuidVisitor)(NSUUID *uuid))
{
    ssize_t readed;

    macho_header<T> mh;
    if (size < sizeof(mh)) return log_vv("file is too small");
    readed = pread_all(fd, &mh, sizeof(mh), offset);
    if (readed != sizeof(mh)) return log_vv("pread failed");

    uint32_t sizeofcmds = mh.sizeofcmds();
    size -= sizeof(mh);
    offset += sizeof(mh);
    if (size < sizeofcmds) return log_vv("file is badly formed");

    uint8_t *cmdp = (uint8_t *)malloc(sizeofcmds);
    if (!cmdp) return log_vv("malloc(sizeofcmds) failed");

    readed = pread_all(fd, cmdp, sizeofcmds, offset);
    if (readed == sizeofcmds) {
        uint8_t *cmds = cmdp;
        for (uint32_t c = 0; c < mh.ncmds(); c++) {
            macho_load_command<T> *cmd;
            if (size < sizeof(*cmd)) return log_vv("file is badly formed");
            cmd = (macho_load_command<T>*) cmds;
            if (size < cmd->cmdsize()) return log_vv("file is badly formed");
            cmds += cmd->cmdsize();
            size -= cmd->cmdsize();

            if (dylibVisitor  &&  
                (cmd->cmd() == LC_LOAD_DYLIB  ||  
                 cmd->cmd() == LC_LOAD_WEAK_DYLIB  ||  
                 cmd->cmd() == LC_LAZY_LOAD_DYLIB))
            {
                macho_dylib_command<T>* dylib = (macho_dylib_command<T>*)cmd;
                if (dylib->cmdsize() < dylib->name_offset()) continue;
                char *name = (char *)dylib + dylib->name_offset();
                size_t name_len =
                    strnlen(name, dylib->cmdsize() - dylib->name_offset());
                log_vv("  loads %.*s", (int)name_len, name);

                #define PREPREFIX "@rpath/"
                #define PREFIX    PREPREFIX "libswift"
                if (0 == strncmp(name, PREFIX, strlen(PREFIX))) {
                    NSString *nsname = 
                        [[[[NSString alloc] initWithBytes:name length:name_len 
                           encoding:NSUTF8StringEncoding] autorelease]
                         substringFromIndex:strlen(PREPREFIX)];
                    if (nsname) dylibVisitor(nsname);
                }
            }
            else if (uuidVisitor  &&  cmd->cmd() == LC_UUID) {
                macho_uuid_command<T>* uuid_cmd = (macho_uuid_command<T>*)cmd;
                if (uuid_cmd->cmdsize() < sizeof(uuid_command)) continue;
                CFUUIDBytes uuid_bytes = *(const CFUUIDBytes *)uuid_cmd->uuid();
                NSUUID *uuid = (NSUUID *)
                    CFUUIDCreateFromUUIDBytes(nil, uuid_bytes);
                uuidVisitor(uuid);
                [uuid release];
            }
        }
    }
    free(cmdp);

    return 0;
}


int parse_macho(int fd, uint32_t offset, uint32_t size, 
              void (^dylibVisitor)(NSString *path), 
              void (^uuidVisitor)(NSUUID *uuid))
{
    uint32_t magic;
    if (size < sizeof(magic)) return log_vv("file is too small");
    ssize_t readed = pread_all(fd, &magic, sizeof(magic), offset);
    if (readed != sizeof(magic)) return log_vv("pread failed");
    
    switch (magic) {
    case MH_MAGIC_64:
        return parse_macho<Pointer64<CurrentEndian>>(fd, offset, size, 
                                                     dylibVisitor, uuidVisitor);
    case MH_MAGIC:
        return parse_macho<Pointer32<CurrentEndian>>(fd, offset, size, 
                                                     dylibVisitor, uuidVisitor);
    case MH_CIGAM_64:
        return parse_macho<Pointer64<OtherEndian>>(fd, offset, size, 
                                                   dylibVisitor, uuidVisitor);
    case MH_CIGAM:
        return parse_macho<Pointer32<OtherEndian>>(fd, offset, size, 
                                                   dylibVisitor, uuidVisitor);
    default:
        return log_vv("file is not mach-o");
    }
}


int parse_fat(int fd, off_t fsize, char *buffer, size_t size, 
              void (^dylibVisitor)(NSString *path), 
              void (^uuidVisitor)(NSUUID *uuid))
{
    uint32_t magic;

    if (size < sizeof(magic)) {
        return log_vv("file is too small");
    }

    magic = *(uint32_t *)buffer;
    if (magic == FAT_MAGIC || magic == FAT_CIGAM) {
        struct fat_header *fh;
        uint32_t fat_magic, fat_nfat_arch;
        struct fat_arch *archs;
        uint32_t i;
        
        if (size < sizeof(struct fat_header)) {
            return log_vv("file is too small");
        }

        fh = (struct fat_header *)buffer;
        fat_magic = OSSwapBigToHostInt32(fh->magic);
        fat_nfat_arch = OSSwapBigToHostInt32(fh->nfat_arch);

        size_t fat_arch_size;
        // fat_nfat_arch * sizeof(struct fat_arch) + sizeof(struct fat_header)
        if (os_mul_and_add_overflow(fat_nfat_arch, sizeof(struct fat_arch),
                                    sizeof(struct fat_header), &fat_arch_size))
        {
            return log_vv("too many fat archs\n");
        }
        if (size < fat_arch_size) {
            return log_vv("file is too small");
        }

        archs = (struct fat_arch *)(buffer + sizeof(struct fat_header));

        /* Special case hidden CPU_TYPE_ARM64 */
        size_t fat_arch_plus_one_size;
        if (os_add_overflow(fat_arch_size, sizeof(struct fat_arch),
                            &fat_arch_plus_one_size))
        {
            return log_vv("too many fat archs\n");
        }
        if (size >= fat_arch_plus_one_size) {
            if (fat_nfat_arch > 0
                && OSSwapBigToHostInt32(archs[fat_nfat_arch].cputype) == CPU_TYPE_ARM64) {
                fat_nfat_arch++;
            }
        }
        /* End special case hidden CPU_TYPE_ARM64 */

        for (i=0; i < fat_nfat_arch; i++) {
            int ret;
            uint32_t arch_cputype, arch_cpusubtype, arch_offset, arch_size, arch_align;

            arch_cputype = OSSwapBigToHostInt32(archs[i].cputype);
            arch_cpusubtype = OSSwapBigToHostInt32(archs[i].cpusubtype);
            arch_offset = OSSwapBigToHostInt32(archs[i].offset);
            arch_size = OSSwapBigToHostInt32(archs[i].size);
            arch_align = OSSwapBigToHostInt32(archs[i].align);

            /* Check that slice data is after all fat headers and archs */
            if (arch_offset < fat_arch_size) {
                return log_vv("file is badly formed");
            }

            /* Check that the slice ends before the file does */
            if (arch_offset > fsize) {
                return log_vv("file is badly formed");
            }

            if (arch_size > fsize) {
                return log_vv("file is badly formed");
            }

            if (arch_offset > (fsize - arch_size)) {
                return log_vv("file is badly formed");
            }

            ret = parse_macho(fd, arch_offset, arch_size,
                              dylibVisitor, uuidVisitor);
            if (ret != 0) {
                return ret;
            }
        }
        return 0;
    } else {
        /* Not a fat file */
        return parse_macho(fd, 0, fsize, dylibVisitor, uuidVisitor);
    }
}


void process(NSString *path, void(^dylibVisitor)(NSString *), 
             void (^uuidVisitor)(NSUUID *))
{
    log_vv("Scanning %s...", path.fileSystemRepresentation);

    int fd = open(path.fileSystemRepresentation, O_RDONLY);
    if (fd < 0) log_vv("%s: open failed: %s", 
                       path.fileSystemRepresentation, strerror(errno));

    struct stat st;
    if (fstat(fd, &st) < 0) {
        log_vv("%s: stat failed: %s", 
               path.fileSystemRepresentation, strerror(errno));
    } else {
        const int len = 4096;
        char buf[len];
        ssize_t readed = pread_all(fd, buf, len, 0);
        if (readed != len) {
            log_vv("%s: pread failed: %s", 
                   path.fileSystemRepresentation, strerror(errno));
        } else {
            parse_fat(fd, st.st_size, buf, len, dylibVisitor, uuidVisitor);
        }
    }
    close(fd);
}


@implementation NSString (sst)
-(NSString *)sst_stringByAppendingPathComponents:(NSArray *)components
{
    NSString *result = self;
    @autoreleasepool {
        for (NSString *component in components) {
            result = [result stringByAppendingPathComponent:component];
        }
        [result retain];
    }
    return [result autorelease];
}
@end

@implementation NSTask (sst)
-(NSString *)sst_command {
    NSMutableString *command = [self.launchPath mutableCopy];
    for (NSString *arg in self.arguments) {
        [command appendFormat:@" '%@'", arg];
    }
    return command;
}
@end


bool operator <= (const struct timespec &lhs, const struct timespec &rhs) 
{
    if (lhs.tv_sec == rhs.tv_sec) return lhs.tv_nsec <= rhs.tv_nsec;
    return lhs.tv_sec <= rhs.tv_sec;
}


// This executable's own path.
NSString *self_executable = []() -> NSString * {
    uint32_t len = 0;
    _NSGetExecutablePath(nil, &len);
    char buf[len];
    _NSGetExecutablePath(buf, &len);
    return [[NSString alloc] initWithUTF8String:buf];
}();


// This executable's own xctoolchain path.
NSString *self_toolchain = []() -> NSString * {
    @autoreleasepool {
        NSString *result = self_executable;
        
        // Remove the executable name.
        result = result.stringByDeletingLastPathComponent;
        
        // Remove trailing /usr/bin, if any
        if ([result.lastPathComponent isEqualToString:@"bin"]) {
            result = result.stringByDeletingLastPathComponent;
        }
        if ([result.lastPathComponent isEqualToString:@"usr"]) {
            result = result.stringByDeletingLastPathComponent;
        }
        return [result retain];
    }
}();


// Runs a tool with `xcrun`. 
// Returns NSTask.terminationStatus.
// Prints the tool's command line if we are verbose.
// Prints the tool's stdout and stderr if terminationStatus is non-zero
//   or if we are very verbose.
typedef void (^XcrunToolBlock)(NSData *stdOutData, NSData *stdErrorData, int err);

int xcrunToolCommand(NSArray *commandAndArguments, XcrunToolBlock block = 0)
{
    @autoreleasepool {
        NSTask *task = [[[NSTask alloc] init] autorelease];
        task.launchPath = @"/usr/bin/xcrun";

        // Tell xcrun to search our toolchain first.
        NSMutableArray *arguments = 
            [[commandAndArguments mutableCopy] autorelease];
        [arguments insertObject:@"--toolchain" atIndex:0];
        [arguments insertObject:self_toolchain atIndex:1];

        // Tell xcrun to print its command if we are very verbose.
        if (Verbose > 1) {
            [arguments insertObject:@"--log" atIndex:2];
        }

        task.arguments = arguments;
        
        NSPipe *outPipe = [NSPipe pipe];
        NSPipe *errPipe = [NSPipe pipe];
        task.standardOutput = outPipe;
        task.standardError = errPipe;
        
        log_v("  %s", task.sst_command.fileSystemRepresentation);
        [task launch];

        // Read stdout and stderr in parallel, then wait for the task 
        // to exit. Anything else risks deadlock if the task fills 
        // one of the output buffers.

        __block NSData *stdErrData = nil;
        dispatch_semaphore_t gotStdErr = dispatch_semaphore_create(0);
        dispatch_queue_t concurrentQueue = 
            dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
        dispatch_async(concurrentQueue, ^{
            stdErrData = 
                [[errPipe.fileHandleForReading readDataToEndOfFile] retain];
            dispatch_semaphore_signal(gotStdErr);
        });

        NSData *stdOutData = [outPipe.fileHandleForReading readDataToEndOfFile];

        dispatch_semaphore_wait(gotStdErr, DISPATCH_TIME_FOREVER);
        dispatch_release(gotStdErr);
        [stdErrData autorelease];

        [task waitUntilExit];
        
        // Task is finished and we have its stdout and stderr output.

        // Print its stdout and stderr if it failed or we are verbose.
        // (Print nothing by default because codesign is noisy.)

        int err = task.terminationStatus;
        if (err  ||  Verbose > 1) {
            fwrite(stdErrData.bytes, stdErrData.length, 1, stdout);
            fwrite(stdOutData.bytes, stdOutData.length, 1, stdout);
        }
        if (block) { block(stdOutData, stdErrData, err); }
        return err;
    }
}


void copyAndStripBitcode(NSString *src, NSString *dst)
{
    // -r removes bitcode
    int err = xcrunToolCommand(@[@"bitcode_strip", src, @"-r", @"-o", dst]);

    // Fail if bitcode_strip failed.
    if (err) {
        fail("Couldn't copy and strip bitcode %s to %s: bitcode_strip failed "
             "with exit code %d", 
             src.fileSystemRepresentation, dst.fileSystemRepresentation, err);
    }
}


void 
copyFile(NSFileManager *fm, NSString *src, NSString *dst, bool stripBitcode)
{
    if (stripBitcode) {
        copyAndStripBitcode(src, dst);
    } else {
        NSError *nserr;
        if (![fm copyItemAtPath:src toPath:dst error:&nserr]) {
            fail("Couldn't copy %s to %s: %s", 
                 src.fileSystemRepresentation, 
                 dst.fileSystemRepresentation, 
                 nserr.localizedFailureReason.UTF8String);
        }
    }
}


void copyLibraries(NSString *src_dir, NSString *dst_dir, 
                   NSMutableDictionary *libs, bool stripBitcode)
{
    NSFileManager *fm = NSFileManager.defaultManager;

    [fm createDirectoryAtPath: dst_dir withIntermediateDirectories:YES 
     attributes:nil error:nil];
    
    for (NSString *lib in libs) @autoreleasepool {
        NSString *src = [src_dir stringByAppendingPathComponent:lib]; 
        NSString *dst = [dst_dir stringByAppendingPathComponent:lib];
        
        // Compare UUIDs of src and dst and don't copy if they're the same.
        // Do not use mod times for this task: the dst copy gets code-signed 
        // and bitcode-stripped so it can look newer than it really is.
        NSSet *srcUUIDs = libs[lib];
        NSMutableSet *dstUUIDs = [NSMutableSet set];
        process(dst, nil, ^(NSUUID *uuid) {
            [dstUUIDs addObject:uuid];
        });

        log_vv("Source UUIDs %s: %s", src.fileSystemRepresentation, 
               srcUUIDs.description.UTF8String);
        log_vv("Destination UUIDs %s: %s", dst.fileSystemRepresentation, 
               dstUUIDs.description.UTF8String);

        if ([srcUUIDs isEqualToSet:dstUUIDs]) {
            log_v("%s is up to date at %s", 
                  lib.fileSystemRepresentation, dst.fileSystemRepresentation);
            continue;
        }
        
        // Perform the copy.
        
        log_v("Copying %s from %s to %s", 
              lib.fileSystemRepresentation, 
              src_dir.fileSystemRepresentation, 
              dst_dir.fileSystemRepresentation);
        
        [fm removeItemAtPath:dst error:nil];  // fixme report this err?
        copyFile(fm, src.stringByResolvingSymlinksInPath, dst, stripBitcode);
    }
}

NSString *relative_path(NSString *base, NSString *suffix_name)
{
    NSDictionary *env = NSProcessInfo.processInfo.environment;
    NSString *suffix = env[suffix_name];
    if (base && suffix) {
        return [base stringByAppendingPathComponent:suffix];
    }
    return nil;
}

void add_relative_path(NSMutableArray *paths, 
                       NSString *base, NSString *suffix_name)
{
    NSString *path = relative_path(base, suffix_name);
    if (path) [paths addObject:path];
}

NSData *query_code_signature(NSString *file) {
    __block NSData *d = 0;
    @autoreleasepool {
          NSArray *command = @[ @"codesign", @"-r-", @"--display", file];
          log_v("Probing signature of %s", file.fileSystemRepresentation);
          int err = xcrunToolCommand(command,
             ^(NSData *stdOutData, NSData *stdErrData, int err) {
                if (!err) { d = [stdOutData retain]; }
          });
          if (err) { return 0; }
    }
    return [d autorelease];
}

int main(int argc, const char *argv[])
{
    @autoreleasepool {
        NSFileManager *fm = [NSFileManager defaultManager];

        // Exxecutables to scan for Swift references.
        // --scan-executable
        NSMutableArray *executables = [NSMutableArray array];

        // Directories to scan for more executables.
        // --scan-folder
        NSMutableArray *embedDirs = [NSMutableArray array];

        // Platform name.
        // --platform
        // or the last path component of --source-libraries
        NSString *platform = nil;

        // Copy source.
        // --source-libraries
        // or /path/to/swift-stdlib-tool/../../lib/swift/<--platform>
        NSString *src_dir = nil;

        // Copy destinations, signed and unsigned.
        // --destination and --unsigned-destination
        NSString *dst_dir = nil;
        NSString *unsigned_dst_dir = nil;

        // Resource copy destination.
        // --resource-destination
        NSString *resource_dst_dir = nil;

        // Resource libraries.
        // --resource-library
        NSMutableArray *resourceLibraries = [NSMutableArray new];

        // Code signing options.
        NSString *ident = nil;
        NSString *keychain = nil;
        NSMutableArray *otherCodesignFlags = [NSMutableArray array];

        // Read arguments
        bool print = false;
        bool copy = false;
        bool stripBitcode = false;
        for (int i = 1; i < argc; i++) {
            if (0 == strcmp(argv[i], "--print")) print = true;
            if (0 == strcmp(argv[i], "--copy")) copy = true;
            if (0 == strcmp(argv[i], "--verbose")) Verbose++;
            if (0 == strcmp(argv[i], "--help")) {
                printUsage();
                exit(0);
            }

            if (0 == strcmp(argv[i], "--scan-executable")) {
                [executables addObject:[NSString stringWithUTF8String:argv[++i]]];
            }
            if (0 == strcmp(argv[i], "--scan-folder")) {
                [embedDirs addObject:[NSString stringWithUTF8String:argv[++i]]];
            }
            if (0 == strcmp(argv[i], "--source-libraries")) {
                src_dir = [NSString stringWithUTF8String:argv[++i]];
            }
            if (0 == strcmp(argv[i], "--platform")) {
                platform = [NSString stringWithUTF8String:argv[++i]];
            }

            if (0 == strcmp(argv[i], "--destination")) {
                dst_dir = [NSString stringWithUTF8String:argv[++i]];
            }
            if (0 == strcmp(argv[i], "--unsigned-destination")) {
                unsigned_dst_dir = [NSString stringWithUTF8String:argv[++i]];
            }

            if (0 == strcmp(argv[i], "--sign")) {
                ident = [NSString stringWithUTF8String:argv[++i]];
            }
            if (0 == strcmp(argv[i], "--keychain")) {
                keychain = [NSString stringWithUTF8String:argv[++i]];
            }
            if (0 == strcmp(argv[i], "--Xcodesign")) {
                [otherCodesignFlags addObject:
                 [NSString stringWithUTF8String:argv[++i]]];
            }

            if (0 == strcmp(argv[i], "--strip-bitcode")) {
                stripBitcode = true;
            }

            if (0 == strcmp(argv[i], "--resource-destination")) {
                resource_dst_dir = [NSString stringWithUTF8String:argv[++i]];
            }
            if (0 == strcmp(argv[i], "--resource-library")) {
                [resourceLibraries addObject:[NSString stringWithUTF8String:argv[++i]]];
            }
        }

        // Fix up src_dir and platform values.
        if (!src_dir && !platform) {
            // Neither src_dir nor platform is set. Die.
            fail_usage("At least one of --source-libraries and --platform "
                       "must be set.");
        }
        else if (!src_dir) {
            // platform is set but src_dir is not. 
            // Use platform to set src_dir relative to us.
            src_dir = [[[self_executable stringByDeletingLastPathComponent]
                        stringByDeletingLastPathComponent]
                       sst_stringByAppendingPathComponents:
                       @[ @"lib", @"swift", platform ]];
        } else if (!platform) {
            // src_dir is set but platform is not. 
            // Pick platform from src_dir's name.
            platform = src_dir.lastPathComponent;
        }

        // Add the platform to unsigned_dst_dir if it is not already present.
        if (unsigned_dst_dir) {
            NSString *unsigned_platform = unsigned_dst_dir.lastPathComponent;
            if (![platform isEqualToString:unsigned_platform]) {
                unsigned_dst_dir = 
                    [unsigned_dst_dir stringByAppendingPathComponent:platform];
            }
        }
        
        // If the user specifies --strip-bitcode but not --sign, this
        // will cause the dylibs to get copied, stripped, but not resigned.
        // This will cause apps to fail to launch because the code signature
        // is invalid.  In this case, ignore --strip-bitcode.
        if (stripBitcode && !ident) {
            stripBitcode = false;
        }

        // Collect executables from the --scan-folder locations.
        for (NSString *embedDir in embedDirs) @autoreleasepool {
            NSDirectoryEnumerator *dir = [fm enumeratorAtPath:embedDir];
            for (NSString *p in dir) @autoreleasepool {
                BOOL isDir;
                NSString *p2 = [embedDir stringByAppendingPathComponent:p];
                if ([fm fileExistsAtPath:p2 isDirectory:&isDir]  &&  
                    !isDir  &&  
                    [fm isExecutableFileAtPath:p2])
                {
                    [executables addObject:p2];
                } else {
                    log_vv("%s is not an executable file", 
                           p2.fileSystemRepresentation);
                }
            }
        }
             
        // Collect Swift library names from the input files.
        // If the library does not exist in src_dir then assume the user wrote 
        // their own library named libswift* and is handling it elsewhere.
        NSMutableDictionary *swiftLibs = [NSMutableDictionary new];
        for (NSString *path in executables) @autoreleasepool {
            process(path, 
               ^(NSString *linkedLib) { 
                    @autoreleasepool {
                        NSString *linkedSrc =
                            [src_dir stringByAppendingPathComponent:linkedLib];
                        if ([fm fileExistsAtPath:linkedSrc]) {
                            swiftLibs[linkedLib] = [NSMutableSet set]; 
                        }
                    }
                }, 
                nil);
        }

        // Collect more Swift library names from the Swift libraries themselves.
        // Also collect the Swift libraries' UUIDs.
        NSMutableArray *worklist = [swiftLibs.allKeys mutableCopy];
        while (worklist.count) @autoreleasepool {
            NSString *lib = [worklist lastObject];
            [worklist removeLastObject];
            NSString *path = [src_dir stringByAppendingPathComponent:lib];
            process(path, 
                ^(NSString *linkedLib) {
                    @autoreleasepool {
                        NSString *linkedSrc = 
                            [src_dir stringByAppendingPathComponent:linkedLib];
                        if (!swiftLibs[linkedLib]  &&  
                            [fm fileExistsAtPath:linkedSrc]) 
                        {
                            swiftLibs[linkedLib] = [NSMutableSet set];
                            [worklist addObject:linkedLib];
                        }
                    }
                }, 
                ^(NSUUID *uuid) {
                    NSMutableSet *uuids = swiftLibs[lib];
                    [uuids addObject:uuid];
                });
        }
        [worklist release];

        // Collect all the Swift libraries that the user requested
        // with --resource-library.
        NSMutableDictionary *swiftLibsForResources = [NSMutableDictionary new];
        for (NSString *lib in resourceLibraries) @autoreleasepool {
            NSString *libSrc = [src_dir stringByAppendingPathComponent:lib];
            if ([fm fileExistsAtPath:libSrc]) {
                swiftLibsForResources[lib] = [NSMutableSet set];
            }
        }

        // Collect dependencies of --resource-library libs.
        worklist = [swiftLibsForResources.allKeys mutableCopy];
        while (worklist.count) @autoreleasepool {
            NSString *lib = [worklist lastObject];
            [worklist removeLastObject];
            NSString *path = [src_dir stringByAppendingPathComponent:lib];
            process(path,
                ^(NSString *linkedLib) {
                    NSString *linkedSrc =
                        [src_dir stringByAppendingPathComponent:linkedLib];
                    if (!swiftLibsForResources[linkedLib] &&
                        [fm fileExistsAtPath:linkedSrc])
                    {
                        swiftLibsForResources[linkedLib] = [NSMutableSet set];
                        [worklist addObject:linkedLib];
                    }
                },
                ^(NSUUID *uuid) {
                    NSMutableSet *uuids = swiftLibsForResources[lib];
                    [uuids addObject:uuid];
                });
        }
        [worklist release];

        // Print the Swift libraries (full path to toolchain's copy)
        if (print) {
            for (NSString *lib in swiftLibs) {
                printf("%s\n", [[src_dir stringByAppendingPathComponent:lib] 
                                fileSystemRepresentation]);
            }
        }

        // Copy the Swift libraries to $build_dir/$frameworks
        // and $build_dir/$unsigned_frameworks
        if (copy) {
            copyLibraries(src_dir, dst_dir, swiftLibs, stripBitcode);
            if (unsigned_dst_dir) {
                // Never strip bitcode from the unsigned libraries. 
                // Their existing signatures must be preserved.
                copyLibraries(src_dir, unsigned_dst_dir, swiftLibs, false);
            }

            if (resource_dst_dir) {
                // Never strip bitcode from resources libraries, for
                // the same reason as the libraries copied to
                // unsigned_dst_dir.
                copyLibraries(src_dir, resource_dst_dir, swiftLibsForResources, false);
            }
        }

        // Codesign the Swift libraries in $build_dir/$frameworks
        // but not the libraries in $build_dir/$unsigned_frameworks.
        if (ident) {
            // Swift libraries that are up-to-date get codesigned anyway
            // (in case options changed or a previous build was incomplete).
            // We do employ an optimization, however, if resigning the dylib
            // results in getting the same signing identity and credentials
            // then we keep the original file to optimize for delta updates
            // to the device.

            __block bool signedOne = false;
            NSLock *signingLock = [NSLock new];

            [swiftLibs enumerateKeysAndObjectsWithOptions: NSEnumerationConcurrent usingBlock: ^(id key, id value, BOOL *stop) {

                // Work around authentication UI problems
                // by signing one synchronously and then signing the rest.
                [signingLock lock];
                if (signedOne) {
                    // First signer is complete. Proceed concurrently.
                    [signingLock unlock];
                } else {
                    // We are the first signer. Hold the lock until we finish.
                }

                NSString *lib = key;
                NSString *dst = [dst_dir stringByAppendingPathComponent:lib];

                // Get the code signature, and copy the dylib to the side
                // to preserve it in case it does not change.  We can use
                // this to avoid unnecessary copies during delta installs
                // to devices.
                NSData *oldSignatureData = query_code_signature(dst);
                const char *tmpFilePath = 0;
                if (oldSignatureData) {
                    // Make a copy of the existing file, with permissions and
                    // mtime preserved.
                    NSString *tmpFile = [dst stringByAppendingPathExtension:@"original"];
                    tmpFilePath = tmpFile.fileSystemRepresentation;
                    xcrunToolCommand(@[@"cp", @"-p", dst, tmpFile]);
                }

                // Proceed with (re-)codesigning.
                log_v("Codesigning %s at %s", lib.fileSystemRepresentation, dst_dir.fileSystemRepresentation);

                // Build the codesign invocation.
                NSMutableArray *commandAndArguments = 
                    [NSMutableArray arrayWithObjects:
                     @"codesign", 
                     @"--force", @"--sign", ident, @"--verbose", nil];

                if (keychain) {
                    [commandAndArguments addObject:@"--keychain"];
                    [commandAndArguments addObject:keychain];
                }

                // Other codesign flags come later
                // so they can override the default flags.
                [commandAndArguments addObjectsFromArray:otherCodesignFlags];

                [commandAndArguments addObject:dst];

                int err = xcrunToolCommand(commandAndArguments);

                // Fail if codesign failed.
                if (err) {
                    // Clean up any temporary files.
                    if (tmpFilePath)
                        unlink(tmpFilePath);
                    fail("Couldn't codesign %s: codesign failed with "
                         "exit code %d", dst.fileSystemRepresentation, err);
                }

                // If we have an existing code signature data, query the new one and compare
                // it with the code signature of the file before we re-signed it.
                // If they are the same, use the original file instead.  This preserves
                // the contents of the file and mtime for use with delta installs.
                if (oldSignatureData) {
                    NSData *newSignatureData = query_code_signature(dst);

#if 0
                    // For Debugging.
                    fprintf(stdout, "oldSignature (%lu bytes)\n", (unsigned long)oldSignatureData.length);
                    fwrite(oldSignatureData.bytes, oldSignatureData.length, 1, stdout);
                    fprintf(stdout, "\nnewSignature (%lu bytes)\n", (unsigned long)newSignatureData.length);
                    fwrite(newSignatureData.bytes, newSignatureData.length, 1, stdout);
                    fprintf(stdout, "\n");
                    fflush(stdout);
#endif

                    unsigned newLength = newSignatureData.length;
                    if (newLength == oldSignatureData.length && 
                        memcmp(newSignatureData.bytes, oldSignatureData.bytes, newLength) == 0) {
                        log_v("Code signature of %s is unchanged; keeping original", lib.fileSystemRepresentation);
                        // The two signatures match.  Unlink the new file, and re-link the old file.
                        const char *filePath = dst.fileSystemRepresentation;
                        unlink(filePath);
                        link(tmpFilePath, filePath);
                    }
                }
                // Clean up any temporary files.
                if (tmpFilePath) {
                    unlink(tmpFilePath);
                }

                if (!signedOne) {
                    // We are the first signer. Allow the others to proceed now.
                    signedOne = true;
                    [signingLock unlock];
                }
            }];
            [signingLock release];
        }
    }
    exit(0);
}
