
/*--------------------------------------------------------------------*/
/*--- Launching valgrind                         launcher-darwin.c ---*/
/*--------------------------------------------------------------------*/

/*
   This file is part of Valgrind, a dynamic binary instrumentation
   framework.

   Copyright (C) 2000-2013 Julian Seward 
      jseward@acm.org

   This program is free software; you can redistribute it and/or
   modify it under the terms of the GNU General Public License as
   published by the Free Software Foundation; either version 2 of the
   License, or (at your option) any later version.

   This program is distributed in the hope that it will be useful, but
   WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
   General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
   02111-1307, USA.

   The GNU General Public License is contained in the file COPYING.
*/

/* Note: this is a "normal" program and not part of Valgrind proper,
   and so it doesn't have to conform to Valgrind's arcane rules on
   no-glibc-usage etc. */

#include <assert.h>
#include <ctype.h>
#include <errno.h>
#include <fcntl.h>
#include <libgen.h>
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/mman.h>
#include <sys/param.h>
#include <sys/stat.h>
#include <sys/user.h>
#include <unistd.h>
#include <mach-o/fat.h>
#include <mach-o/loader.h>

#include "pub_core_debuglog.h"
#include "pub_core_vki.h"       // Avoids warnings from pub_core_libcfile.h
#include "pub_core_libcproc.h"  // For VALGRIND_LIB, VALGRIND_LAUNCHER
#include "pub_core_ume.h"

static struct {
   cpu_type_t cputype;
   const char *apple_name;     // e.g. x86_64
   const char *valgrind_name;  // e.g. amd64
} valid_archs[] = {
   { CPU_TYPE_X86,       "i386",   "x86" },
   { CPU_TYPE_X86_64,    "x86_64", "amd64" },
   { CPU_TYPE_ARM,       "arm",    "arm" },
   /* Not that it's actually relevant, since we don't support PPC on
      MacOS X, but .. the Apple PPC descriptors refer to the BE
      variant, since the LE variant is something that appeared long
      after Apple dropped PPC. */
   { CPU_TYPE_POWERPC,   "ppc",    "ppc32" }, 
   { CPU_TYPE_POWERPC64, "ppc64",  "ppc64be" }
};
static int valid_archs_count = sizeof(valid_archs)/sizeof(valid_archs[0]);

static const char *name_for_cputype(cpu_type_t cputype)
{
   int i;
   for (i = 0; i < valid_archs_count; i++) {
      if (valid_archs[i].cputype == cputype) {
         return valid_archs[i].valgrind_name;
      }
   }
   return NULL;
}

/* Report fatal errors */
__attribute__((noreturn))
static void barf ( const char *format, ... )
{
   va_list vargs;

   va_start(vargs, format);
   fprintf(stderr, "valgrind: ");
   vfprintf(stderr, format, vargs);
   fprintf(stderr, "\n");
   va_end(vargs);

   exit(1);
   /*NOTREACHED*/
   assert(0);
}

/* Search the path for the client program */
static const char *find_client(const char *clientname)
{
   static char fullname[PATH_MAX];
   const char *path = getenv("PATH");
   const char *colon;

   while (path)
   {
      if ((colon = strchr(path, ':')) == NULL)
      {
         strcpy(fullname, path);
         path = NULL;
      }
      else
      {
         memcpy(fullname, path, colon - path);
         fullname[colon - path] = '\0';
         path = colon + 1;
      }

      strcat(fullname, "/");
      strcat(fullname, clientname);

      if (access(fullname, R_OK|X_OK) == 0)
         return fullname;
   }

   return clientname;
}

static int fat_has_cputype(struct fat_header *fh, cpu_type_t cputype)
{
   struct fat_arch *fa = (struct fat_arch *)(fh+1);
   uint32_t nfat_arch = ntohl(fh->nfat_arch);
   uint32_t i;
   for (i = 0; i < nfat_arch; i++) {
      if (ntohl(fa[i].cputype) == cputype) return 1;
   }
   return 0;
}

/* Examine the client and work out which arch it is for */
static const char *select_arch(
      const char *clientname, cpu_type_t default_cputype,
      const char *default_arch)
{
   uint8_t buf[4096];
   ssize_t bytes;
   int fd = open(find_client(clientname), O_RDONLY);
   if (fd < 0) {
      barf("%s: %s", clientname, strerror(errno));
   }

   bytes = read(fd, buf, sizeof(buf));
   close(fd);
   if (bytes != sizeof(buf)) {
      return NULL;
   }
   
   // If it's thin, return that arch.
   {
      struct mach_header *mh = (struct mach_header *)buf;
      if (mh->magic == MH_MAGIC  ||  mh->magic == MH_MAGIC_64) {
         return name_for_cputype(mh->cputype);
      } else if (mh->magic == MH_CIGAM  ||  mh->magic == MH_CIGAM_64) {
         return name_for_cputype(OSSwapInt32(mh->cputype));
      }
   }

   // If it's fat, look for a good arch.
   {
      struct fat_header *fh = (struct fat_header *)buf;
      if (ntohl(fh->magic) == FAT_MAGIC) {
         uint32_t nfat_arch = ntohl(fh->nfat_arch);
         int i;
         // If only one fat arch, use it.
         if (nfat_arch == 1) {
            struct fat_arch *fa = (struct fat_arch *)(fh+1);
            return name_for_cputype(ntohl(fa->cputype));
         }
         // Scan fat headers for default arch.
         if (fat_has_cputype(fh, default_cputype)) {
            return default_arch;
         }
         
         // Scan fat headers for any supported arch.
         for (i = 0; i < valid_archs_count; i++) {
            if (fat_has_cputype(fh, valid_archs[i].cputype)) {
               return valid_archs[i].valgrind_name;
            }
         }
      }
   }
   
   return NULL;
}


/* Where we expect to find all our aux files */
static const char *valgrind_lib;

int main(int argc, char** argv, char** envp)
{
   int i, j, loglevel;
   const char *toolname = NULL;
   const char *clientname = NULL;
   int clientname_arg = 0;
   const char *archname = NULL;
   const char *arch;
   const char *default_arch;
   cpu_type_t default_cputype;
   char *toolfile;
   char launcher_name[PATH_MAX+1];
   char* new_line;
   char* set_cwd;
   char* cwd;
   char** new_env;
   char **new_argv;
   int new_argc;

   /* Start the debugging-log system ASAP.  First find out how many 
      "-d"s were specified.  This is a pre-scan of the command line.
      At the same time, look for the tool name. */
   loglevel = 0;
   for (i = 1; i < argc; i++) {
      if (argv[i][0] != '-') {
         clientname = argv[i];
         clientname_arg = i;
         break;
      }
      if (0 == strcmp(argv[i], "--")) {
         if (i+1 < argc) {
            clientname = argv[i+1];
            clientname_arg = i;
         }
         break;
      }
      if (0 == strcmp(argv[i], "-d")) 
         loglevel++;
      if (0 == strncmp(argv[i], "--tool=", 7)) 
         toolname = argv[i] + 7;
      if (0 == strncmp(argv[i], "--arch=", 7))
         archname = argv[i] + 7;
   }

   /* ... and start the debug logger.  Now we can safely emit logging
      messages all through startup. */
   VG_(debugLog_startup)(loglevel, "Stage 1");

   /* Make sure we know which tool we're using */
   if (toolname) {
      VG_(debugLog)(1, "launcher", "tool '%s' requested\n", toolname);
   } else {
      VG_(debugLog)(1, "launcher", 
                       "no tool requested, defaulting to 'memcheck'\n");
      toolname = "memcheck";
   }

   /* Find the real executable if clientname is an app bundle. */
   if (clientname) {
      struct stat st;
      if (0 == stat(clientname, &st)  &&  (st.st_mode & S_IFDIR)) {
         char *copy = strdup(clientname);
         char *appname = basename(copy);
         char *dot = strrchr(appname, '.');
         if (dot) {
            char *newclient;
            *dot = '\0';
            asprintf(&newclient, "%s/Contents/MacOS/%s", clientname, appname);
            VG_(debugLog)(1, "launcher", "Using executable in app bundle: %s\n", newclient);
            clientname = newclient;
            argv[clientname_arg] = newclient;
         }
         free(copy);
      }
   }

   /* Establish the correct VALGRIND_LIB. */
   {  const char *cp;
      cp = getenv(VALGRIND_LIB);
      valgrind_lib = ( cp == NULL ? VG_LIBDIR : cp );
      VG_(debugLog)(1, "launcher", "valgrind_lib = %s\n", valgrind_lib);
   }

   /* Find installed architectures. Use vgpreload_core-<platform>.so as the
    * indicator of whether the platform is installed. */
   for (i = 0; i < valid_archs_count; i++) {
      char *vgpreload_core;
      asprintf(&vgpreload_core, "%s/vgpreload_core-%s-darwin.so", valgrind_lib, valid_archs[i].valgrind_name);
      if (access(vgpreload_core, R_OK|X_OK) != 0) {
         VG_(debugLog)(1, "launcher", "arch '%s' IS NOT installed\n", valid_archs[i].valgrind_name);
         bzero(&valid_archs[i], sizeof(valid_archs[i]));
      } else {
         VG_(debugLog)(1, "launcher", "arch '%s' IS installed\n", valid_archs[i].valgrind_name);
      }
      free(vgpreload_core);
   }

   /* Find the "default" arch (VGCONF_ARCH_PRI from configure). 
      This is the preferred arch from fat files and the fallback. */
   default_arch = NULL;
   default_cputype = 0;
   for (i = 0; i < valid_archs_count; i++) {
      if (!valid_archs[i].cputype) continue;
      if (0 == strncmp(VG_PLATFORM, valid_archs[i].valgrind_name, 
                       strlen(valid_archs[i].valgrind_name))) 
      {
         default_arch = valid_archs[i].valgrind_name;
         default_cputype = valid_archs[i].cputype;
         break;
      }
   }
   if (i == valid_archs_count) barf("Unknown/uninstalled VG_PLATFORM '%s'", VG_PLATFORM);
   assert(NULL != default_arch);
   assert(0 != default_cputype);

   /* Work out what arch to use, or use the default arch if not possible. */
   if (archname != NULL) {
      // --arch from command line
      arch = NULL;
      for (i = 0; i < valid_archs_count; i++) {
         if (0 == strcmp(archname, valid_archs[i].apple_name)  ||  
             0 == strcmp(archname, valid_archs[i].valgrind_name))
         {
            arch = valid_archs[i].valgrind_name;
            break;
         }
      }
      if (i == valid_archs_count) barf("Unknown --arch '%s'", archname);
      assert(NULL != arch);
      VG_(debugLog)(1, "launcher", "using arch '%s' from --arch=%s\n", 
                    arch, archname);
   } 
   else if (clientname == NULL) {
      // no client executable; use default as fallback
      VG_(debugLog)(1, "launcher", 
                       "no client specified, defaulting arch to '%s'\n",
                        default_arch);
      arch = default_arch;
   } 
   else if ((arch = select_arch(clientname, default_cputype,default_arch))) {
      // arch from client executable
      VG_(debugLog)(1, "launcher", "selected arch '%s'\n", arch);
   } 
   else {
      // nothing found in client executable; use default as fallback
      VG_(debugLog)(1, "launcher", 
                       "no arch detected, defaulting arch to '%s'\n",
                       default_arch);
      arch = default_arch;
   }
   
   cwd = getcwd(NULL, 0);
   if (!cwd) barf("Current directory no longer exists.");

   /* Figure out the name of this executable (viz, the launcher), so
      we can tell stage2.  stage2 will use the name for recursive
      invokations of valgrind on child processes. */
   memset(launcher_name, 0, PATH_MAX+1);
   for (i = 0; envp[i]; i++) 
       ; /* executable path is after last envp item */
   /* envp[i] == NULL ; envp[i+1] == executable_path */
   if (envp[i+1][0] != '/') {
      strcpy(launcher_name, cwd);
      strcat(launcher_name, "/");
   }
   if (strlen(launcher_name) + strlen(envp[i+1]) > PATH_MAX)
      barf("launcher path is too long");
   strcat(launcher_name, envp[i+1]);
   VG_(debugLog)(1, "launcher", "launcher_name = %s\n", launcher_name);

   /* tediously augment the env: VALGRIND_LAUNCHER=launcher_name */
   asprintf(&new_line, VALGRIND_LAUNCHER "=%s", launcher_name);

   /* tediously augment the env: VALGRIND_STARTUP_PWD_%PID_XYZZY=current_working_dir */
   asprintf(&set_cwd, "VALGRIND_STARTUP_PWD_%u_XYZZY=%s", getppid(), cwd);

   // Note that Apple binaries get a secret fourth arg, "char* apple", which
   // contains the executable path.  Don't forget about it.
   for (j = 0; envp[j]; j++)
      ;
   new_env = malloc((j+4) * sizeof(char*));
   if (new_env == NULL)
      barf("malloc of new_env failed.");
   for (i = 0; i < j; i++)
      new_env[i] = envp[i];
   new_env[i++] = new_line;
   new_env[i++] = set_cwd;
   new_env[i++] = NULL;
   new_env[i  ] = envp[i-2]; // the 'apple' arg == the executable_path
   assert(i == j+3);

   /* tediously edit env: hide dyld options from valgrind's captive dyld */
   for (i = 0; envp[i]; i++) {
      if (0 == strncmp(envp[i], "DYLD_", 5)) {
         envp[i][0] = 'V';  /* VYLD_; changed back by initimg-darwin */
      }
   }

   /* tediously edit argv: remove --arch= */
   new_argv = malloc((1+argc) * sizeof(char *));
   for (i = 0, new_argc = 0; i < argc; i++) {
      if (0 == strncmp(argv[i], "--arch=", 7)) {
         // skip
      } else {
         new_argv[new_argc++] = argv[i];
      }
   }
   new_argv[new_argc++] = NULL;

   /* Build the stage2 invokation, and execve it.  Bye! */
   asprintf(&toolfile, "%s/%s-%s-darwin", valgrind_lib, toolname, arch);
   if (access(toolfile, R_OK|X_OK) != 0) {
      barf("tool '%s' not installed (%s) (%s)", toolname, toolfile, strerror(errno));
   }

   VG_(debugLog)(1, "launcher", "launching %s\n", toolfile);

   execve(toolfile, new_argv, new_env);

   fprintf(stderr, "valgrind: failed to start tool '%s' for platform '%s-darwin': %s\n",
                   toolname, arch, strerror(errno));

   exit(1);
}
