Ignore:
Timestamp:
Apr 19, 2011, 11:12:07 PM (14 years ago)
Author:
Yuri Dario
Message:

clamav: update trunk to 0.97.

Location:
clamav/trunk
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • clamav/trunk

  • TabularUnified clamav/trunk/libclamav/c++/llvm/lib/System/Unix/Program.inc

    r189 r319  
    3131#include <fcntl.h>
    3232#endif
     33#ifdef HAVE_POSIX_SPAWN
     34#include <spawn.h>
     35#if !defined(__APPLE__)
     36  extern char **environ;
     37#else
     38#include <crt_externs.h> // _NSGetEnviron
     39#endif
     40#endif
    3341
    3442namespace llvm {
     
    95103
    96104static bool RedirectIO(const Path *Path, int FD, std::string* ErrMsg) {
    97   if (Path == 0)
    98     // Noop
     105  if (Path == 0) // Noop
    99106    return false;
    100   std::string File;
     107  const char *File;
    101108  if (Path->isEmpty())
    102109    // Redirect empty paths to /dev/null
    103110    File = "/dev/null";
    104111  else
    105     File = Path->str();
     112    File = Path->c_str();
    106113
    107114  // Open the file
    108   int InFD = open(File.c_str(), FD == 0 ? O_RDONLY : O_WRONLY|O_CREAT, 0666);
     115  int InFD = open(File, FD == 0 ? O_RDONLY : O_WRONLY|O_CREAT, 0666);
    109116  if (InFD == -1) {
    110     MakeErrMsg(ErrMsg, "Cannot open file '" + File + "' for "
     117    MakeErrMsg(ErrMsg, "Cannot open file '" + std::string(File) + "' for "
    111118              + (FD == 0 ? "input" : "output"));
    112119    return true;
     
    114121
    115122  // Install it as the requested FD
    116   if (-1 == dup2(InFD, FD)) {
     123  if (dup2(InFD, FD) == -1) {
    117124    MakeErrMsg(ErrMsg, "Cannot dup2");
     125    close(InFD);
    118126    return true;
    119127  }
     
    121129  return false;
    122130}
     131
     132#ifdef HAVE_POSIX_SPAWN
     133static bool RedirectIO_PS(const Path *Path, int FD, std::string *ErrMsg,
     134                          posix_spawn_file_actions_t &FileActions) {
     135  if (Path == 0) // Noop
     136    return false;
     137  const char *File;
     138  if (Path->isEmpty())
     139    // Redirect empty paths to /dev/null
     140    File = "/dev/null";
     141  else
     142    File = Path->c_str();
     143
     144  if (int Err = posix_spawn_file_actions_addopen(&FileActions, FD,
     145                            File, FD == 0 ? O_RDONLY : O_WRONLY|O_CREAT, 0666))
     146    return MakeErrMsg(ErrMsg, "Cannot dup2", Err);
     147  return false;
     148}
     149#endif
    123150
    124151static void TimeOutHandler(int Sig) {
     
    151178
    152179bool
    153 Program::Execute(const Path& path,
    154                  const char** args,
    155                  const char** envp,
    156                  const Path** redirects,
    157                  unsigned memoryLimit,
    158                  std::string* ErrMsg)
    159 {
     180Program::Execute(const Path &path, const char **args, const char **envp,
     181                 const Path **redirects, unsigned memoryLimit,
     182                  std::string *ErrMsg) {
     183  // If this OS has posix_spawn and there is no memory limit being implied, use
     184  // posix_spawn.  It is more efficient than fork/exec.
     185#ifdef HAVE_POSIX_SPAWN
     186  if (memoryLimit == 0) {
     187    posix_spawn_file_actions_t FileActions;
     188    posix_spawn_file_actions_init(&FileActions);
     189
     190    if (redirects) {
     191      // Redirect stdin/stdout.
     192      if (RedirectIO_PS(redirects[0], 0, ErrMsg, FileActions) ||
     193          RedirectIO_PS(redirects[1], 1, ErrMsg, FileActions))
     194        return false;
     195      if (redirects[1] == 0 || redirects[2] == 0 ||
     196          *redirects[1] != *redirects[2]) {
     197        // Just redirect stderr
     198        if (RedirectIO_PS(redirects[2], 2, ErrMsg, FileActions)) return false;
     199      } else {       
     200        // If stdout and stderr should go to the same place, redirect stderr
     201        // to the FD already open for stdout.
     202        if (int Err = posix_spawn_file_actions_adddup2(&FileActions, 1, 2))
     203          return !MakeErrMsg(ErrMsg, "Can't redirect stderr to stdout", Err);
     204      }
     205    }
     206
     207    if (!envp)
     208#if !defined(__APPLE__)
     209      envp = const_cast<const char **>(environ);
     210#else
     211      // environ is missing in dylibs.
     212      envp = const_cast<const char **>(*_NSGetEnviron());
     213#endif
     214
     215    pid_t PID;
     216    int Err = posix_spawn(&PID, path.c_str(), &FileActions, /*attrp*/0,
     217                          const_cast<char **>(args), const_cast<char **>(envp));
     218                         
     219    posix_spawn_file_actions_destroy(&FileActions);
     220
     221    if (Err)
     222     return !MakeErrMsg(ErrMsg, "posix_spawn failed", Err);
     223     
     224    Data_ = reinterpret_cast<void*>(PID);
     225    return true;
     226  }
     227#endif
     228 
    160229  if (!path.canExecute()) {
    161230    if (ErrMsg)
     
    201270      // Execute!
    202271      if (envp != 0)
    203         execve(path.c_str(), (char**)args, (char**)envp);
     272        execve(path.c_str(),
     273               const_cast<char **>(args),
     274               const_cast<char **>(envp));
    204275      else
    205         execv(path.c_str(), (char**)args);
     276        execv(path.c_str(),
     277              const_cast<char **>(args));
    206278      // If the execve() failed, we should exit. Follow Unix protocol and
    207279      // return 127 if the executable was not found, and 126 otherwise.
     
    239311  // unlike if we used SIG_IGN.
    240312  if (secondsToWait) {
    241     Act.sa_sigaction = 0;
     313    memset(&Act, 0, sizeof(Act));
    242314    Act.sa_handler = TimeOutHandler;
    243315    sigemptyset(&Act.sa_mask);
    244     Act.sa_flags = 0;
    245316    sigaction(SIGALRM, &Act, &Old);
    246317    alarm(secondsToWait);
Note: See TracChangeset for help on using the changeset viewer.