コード例 #1
0
        /// <exception cref="System.IO.IOException"/>
        public override bool SignalContainer(string user, string pid, ContainerExecutor.Signal
                                             signal)
        {
            VerifyUsernamePattern(user);
            string runAsUser = GetRunAsUser(user);

            string[] command = new string[] { containerExecutorExe, runAsUser, user, Sharpen.Extensions.ToString
                                                  (LinuxContainerExecutor.Commands.SignalContainer.GetValue()), pid, Sharpen.Extensions.ToString
                                                  (signal.GetValue()) };
            Shell.ShellCommandExecutor shExec = new Shell.ShellCommandExecutor(command);
            if (Log.IsDebugEnabled())
            {
                Log.Debug("signalContainer: " + Arrays.ToString(command));
            }
            try
            {
                shExec.Execute();
            }
            catch (Shell.ExitCodeException e)
            {
                int ret_code = shExec.GetExitCode();
                if (ret_code == LinuxContainerExecutor.ResultCode.InvalidContainerPid.GetValue())
                {
                    return(false);
                }
                Log.Warn("Error in signalling container " + pid + " with " + signal + "; exit = "
                         + ret_code, e);
                LogOutput(shExec.GetOutput());
                throw new IOException("Problem signalling container " + pid + " with " + signal +
                                      "; output: " + shExec.GetOutput() + " and exitCode: " + ret_code, e);
            }
            return(true);
        }
コード例 #2
0
        /// <exception cref="System.IO.IOException"/>
        public virtual void MountCgroups(IList <string> cgroupKVs, string hierarchy)
        {
            IList <string> command = new AList <string>(Arrays.AsList(containerExecutorExe, "--mount-cgroups"
                                                                      , hierarchy));

            Sharpen.Collections.AddAll(command, cgroupKVs);
            string[] commandArray = Sharpen.Collections.ToArray(command, new string[command.Count
                                                                ]);
            Shell.ShellCommandExecutor shExec = new Shell.ShellCommandExecutor(commandArray);
            if (Log.IsDebugEnabled())
            {
                Log.Debug("mountCgroups: " + Arrays.ToString(commandArray));
            }
            try
            {
                shExec.Execute();
            }
            catch (IOException e)
            {
                int ret_code = shExec.GetExitCode();
                Log.Warn("Exception in LinuxContainerExecutor mountCgroups ", e);
                LogOutput(shExec.GetOutput());
                throw new IOException("Problem mounting cgroups " + cgroupKVs + "; exit code = "
                                      + ret_code + " and output: " + shExec.GetOutput(), e);
            }
        }
コード例 #3
0
        /// <exception cref="System.IO.IOException"/>
        /// <exception cref="System.Exception"/>
        public override void StartLocalizer(Path nmPrivateContainerTokensPath, IPEndPoint
                                            nmAddr, string user, string appId, string locId, LocalDirsHandlerService dirsHandler
                                            )
        {
            IList <string> localDirs = dirsHandler.GetLocalDirs();
            IList <string> logDirs   = dirsHandler.GetLogDirs();

            VerifyUsernamePattern(user);
            string         runAsUser = GetRunAsUser(user);
            IList <string> command   = new AList <string>();

            AddSchedPriorityCommand(command);
            Sharpen.Collections.AddAll(command, Arrays.AsList(containerExecutorExe, runAsUser
                                                              , user, Sharpen.Extensions.ToString(LinuxContainerExecutor.Commands.InitializeContainer
                                                                                                  .GetValue()), appId, nmPrivateContainerTokensPath.ToUri().GetPath().ToString(),
                                                              StringUtils.Join(",", localDirs), StringUtils.Join(",", logDirs)));
            FilePath jvm = new FilePath(new FilePath(Runtime.GetProperty("java.home"), "bin")
                                        , "java");

            // use same jvm as parent
            command.AddItem(jvm.ToString());
            command.AddItem("-classpath");
            command.AddItem(Runtime.GetProperty("java.class.path"));
            string javaLibPath = Runtime.GetProperty("java.library.path");

            if (javaLibPath != null)
            {
                command.AddItem("-Djava.library.path=" + javaLibPath);
            }
            BuildMainArgs(command, user, appId, locId, nmAddr, localDirs);
            string[] commandArray = Sharpen.Collections.ToArray(command, new string[command.Count
                                                                ]);
            Shell.ShellCommandExecutor shExec = new Shell.ShellCommandExecutor(commandArray);
            if (Log.IsDebugEnabled())
            {
                Log.Debug("initApplication: " + Arrays.ToString(commandArray));
            }
            try
            {
                shExec.Execute();
                if (Log.IsDebugEnabled())
                {
                    LogOutput(shExec.GetOutput());
                }
            }
            catch (Shell.ExitCodeException e)
            {
                int exitCode = shExec.GetExitCode();
                Log.Warn("Exit code from container " + locId + " startLocalizer is : " + exitCode
                         , e);
                LogOutput(shExec.GetOutput());
                throw new IOException("Application " + appId + " initialization failed" + " (exitCode="
                                      + exitCode + ") with output: " + shExec.GetOutput(), e);
            }
        }
コード例 #4
0
ファイル: HardLink.cs プロジェクト: orf53975/hadoop.net
        /// <summary>Retrieves the number of links to the specified file.</summary>
        /// <exception cref="System.IO.IOException"/>
        public static int GetLinkCount(FilePath fileName)
        {
            if (fileName == null)
            {
                throw new IOException("invalid argument to getLinkCount: file name is null");
            }
            if (!fileName.Exists())
            {
                throw new FileNotFoundException(fileName + " not found.");
            }
            // construct and execute shell command
            string[]       cmd       = getHardLinkCommand.LinkCount(fileName);
            string         inpMsg    = null;
            string         errMsg    = null;
            int            exitValue = -1;
            BufferedReader @in       = null;

            Shell.ShellCommandExecutor shexec = new Shell.ShellCommandExecutor(cmd);
            try
            {
                shexec.Execute();
                @in       = new BufferedReader(new StringReader(shexec.GetOutput()));
                inpMsg    = @in.ReadLine();
                exitValue = shexec.GetExitCode();
                if (inpMsg == null || exitValue != 0)
                {
                    throw CreateIOException(fileName, inpMsg, errMsg, exitValue, null);
                }
                if (Shell.Solaris)
                {
                    string[] result = inpMsg.Split("\\s+");
                    return(System.Convert.ToInt32(result[1]));
                }
                else
                {
                    return(System.Convert.ToInt32(inpMsg));
                }
            }
            catch (Shell.ExitCodeException e)
            {
                inpMsg    = shexec.GetOutput();
                errMsg    = e.Message;
                exitValue = e.GetExitCode();
                throw CreateIOException(fileName, inpMsg, errMsg, exitValue, e);
            }
            catch (FormatException e)
            {
                throw CreateIOException(fileName, inpMsg, errMsg, exitValue, e);
            }
            finally
            {
                IOUtils.CloseStream(@in);
            }
        }
コード例 #5
0
        public override void DeleteAsUser(string user, Path dir, params Path[] baseDirs)
        {
            VerifyUsernamePattern(user);
            string         runAsUser = GetRunAsUser(user);
            string         dirString = dir == null ? string.Empty : dir.ToUri().GetPath();
            IList <string> command   = new AList <string>(Arrays.AsList(containerExecutorExe, runAsUser
                                                                        , user, Sharpen.Extensions.ToString(LinuxContainerExecutor.Commands.DeleteAsUser
                                                                                                            .GetValue()), dirString));
            IList <string> pathsToDelete = new AList <string>();

            if (baseDirs == null || baseDirs.Length == 0)
            {
                Log.Info("Deleting absolute path : " + dir);
                pathsToDelete.AddItem(dirString);
            }
            else
            {
                foreach (Path baseDir in baseDirs)
                {
                    Path del = dir == null ? baseDir : new Path(baseDir, dir);
                    Log.Info("Deleting path : " + del);
                    pathsToDelete.AddItem(del.ToString());
                    command.AddItem(baseDir.ToUri().GetPath());
                }
            }
            string[] commandArray = Sharpen.Collections.ToArray(command, new string[command.Count
                                                                ]);
            Shell.ShellCommandExecutor shExec = new Shell.ShellCommandExecutor(commandArray);
            if (Log.IsDebugEnabled())
            {
                Log.Debug("deleteAsUser: "******"DeleteAsUser for " + StringUtils.Join(" ", pathsToDelete) + " returned with exit code: "
                          + exitCode, e);
                Log.Error("Output from LinuxContainerExecutor's deleteAsUser follows:");
                LogOutput(shExec.GetOutput());
            }
        }
コード例 #6
0
        /// <exception cref="System.IO.IOException"/>
        public override void Init()
        {
            // Send command to executor which will just start up,
            // verify configuration/permissions and exit
            IList <string> command = new AList <string>(Arrays.AsList(containerExecutorExe, "--checksetup"
                                                                      ));

            string[] commandArray = Sharpen.Collections.ToArray(command, new string[command.Count
                                                                ]);
            Shell.ShellCommandExecutor shExec = new Shell.ShellCommandExecutor(commandArray);
            if (Log.IsDebugEnabled())
            {
                Log.Debug("checkLinuxExecutorSetup: " + Arrays.ToString(commandArray));
            }
            try
            {
                shExec.Execute();
            }
            catch (Shell.ExitCodeException e)
            {
                int exitCode = shExec.GetExitCode();
                Log.Warn("Exit code from container executor initialization is : " + exitCode, e);
                LogOutput(shExec.GetOutput());
                throw new IOException("Linux container executor not configured properly" + " (error="
                                      + exitCode + ")", e);
            }
            resourcesHandler.Init(this);
        }
コード例 #7
0
 public static bool IsAvailable()
 {
     if (Shell.Windows)
     {
         Shell.ShellCommandExecutor shellExecutor = new Shell.ShellCommandExecutor(new string
                                                                                   [] { Shell.Winutils, "help" });
         try
         {
             shellExecutor.Execute();
         }
         catch (IOException e)
         {
             Log.Error(StringUtils.StringifyException(e));
         }
         finally
         {
             string output = shellExecutor.GetOutput();
             if (output != null && output.Contains("Prints to stdout a list of processes in the task"
                                                   ))
             {
                 return(true);
             }
         }
     }
     return(false);
 }
コード例 #8
0
            /// <summary>Build and execute the resolution command.</summary>
            /// <remarks>
            /// Build and execute the resolution command. The command is
            /// executed in the directory specified by the system property
            /// "user.dir" if set; otherwise the current working directory is used
            /// </remarks>
            /// <param name="args">a list of arguments</param>
            /// <returns>
            /// null if the number of arguments is out of range,
            /// or the output of the command.
            /// </returns>
            protected internal virtual string RunResolveCommand(IList <string> args, string commandScriptName
                                                                )
            {
                int loopCount = 0;

                if (args.Count == 0)
                {
                    return(null);
                }
                StringBuilder allOutput    = new StringBuilder();
                int           numProcessed = 0;

                if (maxArgs < MinAllowableArgs)
                {
                    Log.Warn("Invalid value " + Extensions.ToString(maxArgs) + " for " + ScriptArgCountKey
                             + "; must be >= " + Extensions.ToString(MinAllowableArgs));
                    return(null);
                }
                while (numProcessed != args.Count)
                {
                    int            start   = maxArgs * loopCount;
                    IList <string> cmdList = new AList <string>();
                    cmdList.AddItem(commandScriptName);
                    for (numProcessed = start; numProcessed < (start + maxArgs) && numProcessed < args
                         .Count; numProcessed++)
                    {
                        cmdList.AddItem(args[numProcessed]);
                    }
                    FilePath dir = null;
                    string   userDir;
                    if ((userDir = Runtime.GetProperty("user.dir")) != null)
                    {
                        dir = new FilePath(userDir);
                    }
                    Shell.ShellCommandExecutor s = new Shell.ShellCommandExecutor(Collections.ToArray
                                                                                      (cmdList, new string[cmdList.Count]), dir);
                    try
                    {
                        s.Execute();
                        allOutput.Append(s.GetOutput()).Append(" ");
                    }
                    catch (Exception e)
                    {
                        Log.Warn("Exception running " + s, e);
                        return(null);
                    }
                    loopCount++;
                }
                return(allOutput.ToString());
            }
コード例 #9
0
 internal virtual string GetSystemInfoInfoFromShell()
 {
     Shell.ShellCommandExecutor shellExecutor = new Shell.ShellCommandExecutor(new string
                                                                               [] { Shell.Winutils, "systeminfo" });
     try
     {
         shellExecutor.Execute();
         return(shellExecutor.GetOutput());
     }
     catch (IOException e)
     {
         Log.Error(StringUtils.StringifyException(e));
     }
     return(null);
 }
コード例 #10
0
 // helper method to override while testing
 internal virtual string GetAllProcessInfoFromShell()
 {
     Shell.ShellCommandExecutor shellExecutor = new Shell.ShellCommandExecutor(new string
                                                                               [] { Shell.Winutils, "task", "processList", taskProcessId });
     try
     {
         shellExecutor.Execute();
         return(shellExecutor.GetOutput());
     }
     catch (IOException e)
     {
         Log.Error(StringUtils.StringifyException(e));
     }
     return(null);
 }
コード例 #11
0
        /// <exception cref="System.IO.IOException"/>
        public override int LaunchContainer(Org.Apache.Hadoop.Yarn.Server.Nodemanager.Containermanager.Container.Container
                                            container, Path nmPrivateCotainerScriptPath, Path nmPrivateTokensPath, string user
                                            , string appId, Path containerWorkDir, IList <string> localDirs, IList <string> logDirs
                                            )
        {
            VerifyUsernamePattern(user);
            string      runAsUser      = GetRunAsUser(user);
            ContainerId containerId    = container.GetContainerId();
            string      containerIdStr = ConverterUtils.ToString(containerId);

            resourcesHandler.PreExecute(containerId, container.GetResource());
            string resourcesOptions = resourcesHandler.GetResourcesOption(containerId);

            Shell.ShellCommandExecutor shExec = null;
            try
            {
                Path pidFilePath = GetPidFilePath(containerId);
                if (pidFilePath != null)
                {
                    IList <string> command = new AList <string>();
                    AddSchedPriorityCommand(command);
                    Sharpen.Collections.AddAll(command, Arrays.AsList(containerExecutorExe, runAsUser
                                                                      , user, Sharpen.Extensions.ToString(LinuxContainerExecutor.Commands.LaunchContainer
                                                                                                          .GetValue()), appId, containerIdStr, containerWorkDir.ToString(), nmPrivateCotainerScriptPath
                                                                      .ToUri().GetPath().ToString(), nmPrivateTokensPath.ToUri().GetPath().ToString(),
                                                                      pidFilePath.ToString(), StringUtils.Join(",", localDirs), StringUtils.Join(",",
                                                                                                                                                 logDirs), resourcesOptions));
                    string[] commandArray = Sharpen.Collections.ToArray(command, new string[command.Count
                                                                        ]);
                    shExec = new Shell.ShellCommandExecutor(commandArray, null, container.GetLaunchContext
                                                                ().GetEnvironment());
                    // NM's cwd
                    // sanitized env
                    if (Log.IsDebugEnabled())
                    {
                        Log.Debug("launchContainer: " + Arrays.ToString(commandArray));
                    }
                    shExec.Execute();
                    if (Log.IsDebugEnabled())
                    {
                        LogOutput(shExec.GetOutput());
                    }
                }
                else
                {
                    Log.Info("Container was marked as inactive. Returning terminated error");
                    return(ContainerExecutor.ExitCode.Terminated.GetExitCode());
                }
            }
            catch (Shell.ExitCodeException e)
            {
                int exitCode = shExec.GetExitCode();
                Log.Warn("Exit code from container " + containerId + " is : " + exitCode);
                // 143 (SIGTERM) and 137 (SIGKILL) exit codes means the container was
                // terminated/killed forcefully. In all other cases, log the
                // container-executor's output
                if (exitCode != ContainerExecutor.ExitCode.ForceKilled.GetExitCode() && exitCode
                    != ContainerExecutor.ExitCode.Terminated.GetExitCode())
                {
                    Log.Warn("Exception from container-launch with container ID: " + containerId + " and exit code: "
                             + exitCode, e);
                    StringBuilder builder = new StringBuilder();
                    builder.Append("Exception from container-launch.\n");
                    builder.Append("Container id: " + containerId + "\n");
                    builder.Append("Exit code: " + exitCode + "\n");
                    if (!Optional.FromNullable(e.Message).Or(string.Empty).IsEmpty())
                    {
                        builder.Append("Exception message: " + e.Message + "\n");
                    }
                    builder.Append("Stack trace: " + StringUtils.StringifyException(e) + "\n");
                    if (!shExec.GetOutput().IsEmpty())
                    {
                        builder.Append("Shell output: " + shExec.GetOutput() + "\n");
                    }
                    string diagnostics = builder.ToString();
                    LogOutput(diagnostics);
                    container.Handle(new ContainerDiagnosticsUpdateEvent(containerId, diagnostics));
                }
                else
                {
                    container.Handle(new ContainerDiagnosticsUpdateEvent(containerId, "Container killed on request. Exit code is "
                                                                         + exitCode));
                }
                return(exitCode);
            }
            finally
            {
                resourcesHandler.PostExecute(containerId);
            }
            if (Log.IsDebugEnabled())
            {
                Log.Debug("Output from LinuxContainerExecutor's launchContainer follows:");
                LogOutput(shExec.GetOutput());
            }
            return(0);
        }
コード例 #12
0
        /// <exception cref="System.IO.IOException"/>
        public override int LaunchContainer(Org.Apache.Hadoop.Yarn.Server.Nodemanager.Containermanager.Container.Container
                                            container, Path nmPrivateContainerScriptPath, Path nmPrivateTokensPath, string
                                            userName, string appId, Path containerWorkDir, IList <string> localDirs, IList <string
                                                                                                                            > logDirs)
        {
            string containerImageName = container.GetLaunchContext().GetEnvironment()[YarnConfiguration
                                                                                      .NmDockerContainerExecutorImageName];

            if (Log.IsDebugEnabled())
            {
                Log.Debug("containerImageName from launchContext: " + containerImageName);
            }
            Preconditions.CheckArgument(!Strings.IsNullOrEmpty(containerImageName), "Container image must not be null"
                                        );
            containerImageName = containerImageName.ReplaceAll("['\"]", string.Empty);
            Preconditions.CheckArgument(SaneDockerImage(containerImageName), "Image: " + containerImageName
                                        + " is not a proper docker image");
            string dockerExecutor = GetConf().Get(YarnConfiguration.NmDockerContainerExecutorExecName
                                                  , YarnConfiguration.NmDefaultDockerContainerExecutorExecName);
            FsPermission dirPerm     = new FsPermission(AppdirPerm);
            ContainerId  containerId = container.GetContainerId();
            // create container dirs on all disks
            string containerIdStr = ConverterUtils.ToString(containerId);
            string appIdStr       = ConverterUtils.ToString(containerId.GetApplicationAttemptId().GetApplicationId
                                                                ());

            foreach (string sLocalDir in localDirs)
            {
                Path usersdir     = new Path(sLocalDir, ContainerLocalizer.Usercache);
                Path userdir      = new Path(usersdir, userName);
                Path appCacheDir  = new Path(userdir, ContainerLocalizer.Appcache);
                Path appDir       = new Path(appCacheDir, appIdStr);
                Path containerDir = new Path(appDir, containerIdStr);
                CreateDir(containerDir, dirPerm, true, userName);
            }
            // Create the container log-dirs on all disks
            CreateContainerLogDirs(appIdStr, containerIdStr, logDirs, userName);
            Path tmpDir = new Path(containerWorkDir, YarnConfiguration.DefaultContainerTempDir
                                   );

            CreateDir(tmpDir, dirPerm, false, userName);
            // copy launch script to work dir
            Path launchDst = new Path(containerWorkDir, ContainerLaunch.ContainerScript);

            lfs.Util().Copy(nmPrivateContainerScriptPath, launchDst);
            // copy container tokens to work dir
            Path tokenDst = new Path(containerWorkDir, ContainerLaunch.FinalContainerTokensFile
                                     );

            lfs.Util().Copy(nmPrivateTokensPath, tokenDst);
            string localDirMount         = ToMount(localDirs);
            string logDirMount           = ToMount(logDirs);
            string containerWorkDirMount = ToMount(Sharpen.Collections.SingletonList(containerWorkDir
                                                                                     .ToUri().GetPath()));
            StringBuilder commands   = new StringBuilder();
            string        commandStr = commands.Append(dockerExecutor).Append(" ").Append("run").Append
                                           (" ").Append("--rm --net=host").Append(" ").Append(" --name " + containerIdStr).
                                       Append(localDirMount).Append(logDirMount).Append(containerWorkDirMount).Append(" "
                                                                                                                      ).Append(containerImageName).ToString();
            string dockerPidScript = "`" + dockerExecutor + " inspect --format {{.State.Pid}} "
                                     + containerIdStr + "`";

            // Create new local launch wrapper script
            DockerContainerExecutor.LocalWrapperScriptBuilder sb = new DockerContainerExecutor.UnixLocalWrapperScriptBuilder
                                                                       (this, containerWorkDir, commandStr, dockerPidScript);
            Path pidFile = GetPidFilePath(containerId);

            if (pidFile != null)
            {
                sb.WriteLocalWrapperScript(launchDst, pidFile);
            }
            else
            {
                Log.Info("Container " + containerIdStr + " was marked as inactive. Returning terminated error"
                         );
                return(ContainerExecutor.ExitCode.Terminated.GetExitCode());
            }
            Shell.ShellCommandExecutor shExec = null;
            try
            {
                lfs.SetPermission(launchDst, ContainerExecutor.TaskLaunchScriptPermission);
                lfs.SetPermission(sb.GetWrapperScriptPath(), ContainerExecutor.TaskLaunchScriptPermission
                                  );
                // Setup command to run
                string[] command = GetRunCommand(sb.GetWrapperScriptPath().ToString(), containerIdStr
                                                 , userName, pidFile, this.GetConf());
                if (Log.IsDebugEnabled())
                {
                    Log.Debug("launchContainer: " + commandStr + " " + Joiner.On(" ").Join(command));
                }
                shExec = new Shell.ShellCommandExecutor(command, new FilePath(containerWorkDir.ToUri
                                                                                  ().GetPath()), container.GetLaunchContext().GetEnvironment());
                // sanitized env
                if (IsContainerActive(containerId))
                {
                    shExec.Execute();
                }
                else
                {
                    Log.Info("Container " + containerIdStr + " was marked as inactive. Returning terminated error"
                             );
                    return(ContainerExecutor.ExitCode.Terminated.GetExitCode());
                }
            }
            catch (IOException e)
            {
                if (null == shExec)
                {
                    return(-1);
                }
                int exitCode = shExec.GetExitCode();
                Log.Warn("Exit code from container " + containerId + " is : " + exitCode);
                // 143 (SIGTERM) and 137 (SIGKILL) exit codes means the container was
                // terminated/killed forcefully. In all other cases, log the
                // container-executor's output
                if (exitCode != ContainerExecutor.ExitCode.ForceKilled.GetExitCode() && exitCode
                    != ContainerExecutor.ExitCode.Terminated.GetExitCode())
                {
                    Log.Warn("Exception from container-launch with container ID: " + containerId + " and exit code: "
                             + exitCode, e);
                    LogOutput(shExec.GetOutput());
                    string diagnostics = "Exception from container-launch: \n" + StringUtils.StringifyException
                                             (e) + "\n" + shExec.GetOutput();
                    container.Handle(new ContainerDiagnosticsUpdateEvent(containerId, diagnostics));
                }
                else
                {
                    container.Handle(new ContainerDiagnosticsUpdateEvent(containerId, "Container killed on request. Exit code is "
                                                                         + exitCode));
                }
                return(exitCode);
            }
            finally
            {
                if (shExec != null)
                {
                    shExec.Close();
                }
            }
            return(0);
        }
コード例 #13
0
        /// <param name="testName">name of the test</param>
        /// <param name="numResourceManagers">the number of resource managers in the cluster</param>
        /// <param name="numNodeManagers">the number of node managers in the cluster</param>
        /// <param name="numLocalDirs">the number of nm-local-dirs per nodemanager</param>
        /// <param name="numLogDirs">the number of nm-log-dirs per nodemanager</param>
        /// <param name="enableAHS">enable ApplicationHistoryServer or not</param>
        public MiniYARNCluster(string testName, int numResourceManagers, int numNodeManagers
                               , int numLocalDirs, int numLogDirs, bool enableAHS)
            : base(testName.Replace("$", string.Empty))
        {
            // Number of nm-local-dirs per nodemanager
            // Number of nm-log-dirs per nodemanager
            this.numLocalDirs = numLocalDirs;
            this.numLogDirs   = numLogDirs;
            this.enableAHS    = enableAHS;
            string   testSubDir    = testName.Replace("$", string.Empty);
            FilePath targetWorkDir = new FilePath("target", testSubDir);

            try
            {
                FileContext.GetLocalFSFileContext().Delete(new Path(targetWorkDir.GetAbsolutePath
                                                                        ()), true);
            }
            catch (Exception e)
            {
                Log.Warn("COULD NOT CLEANUP", e);
                throw new YarnRuntimeException("could not cleanup test dir: " + e, e);
            }
            if (Shell.Windows)
            {
                // The test working directory can exceed the maximum path length supported
                // by some Windows APIs and cmd.exe (260 characters).  To work around this,
                // create a symlink in temporary storage with a much shorter path,
                // targeting the full path to the test working directory.  Then, use the
                // symlink as the test working directory.
                string   targetPath = targetWorkDir.GetAbsolutePath();
                FilePath link       = new FilePath(Runtime.GetProperty("java.io.tmpdir"), Runtime.CurrentTimeMillis
                                                       ().ToString());
                string linkPath = link.GetAbsolutePath();
                try
                {
                    FileContext.GetLocalFSFileContext().Delete(new Path(linkPath), true);
                }
                catch (IOException e)
                {
                    throw new YarnRuntimeException("could not cleanup symlink: " + linkPath, e);
                }
                // Guarantee target exists before creating symlink.
                targetWorkDir.Mkdirs();
                Shell.ShellCommandExecutor shexec = new Shell.ShellCommandExecutor(Shell.GetSymlinkCommand
                                                                                       (targetPath, linkPath));
                try
                {
                    shexec.Execute();
                }
                catch (IOException e)
                {
                    throw new YarnRuntimeException(string.Format("failed to create symlink from %s to %s, shell output: %s"
                                                                 , linkPath, targetPath, shexec.GetOutput()), e);
                }
                this.testWorkDir = link;
            }
            else
            {
                this.testWorkDir = targetWorkDir;
            }
            resourceManagers = new ResourceManager[numResourceManagers];
            nodeManagers     = new NodeManager[numNodeManagers];
        }