C# 如果应用程序运行时间超过x,则取消所有任务

C# 如果应用程序运行时间超过x,则取消所有任务,c#,.net,c#-4.0,task,task-parallel-library,C#,.net,C# 4.0,Task,Task Parallel Library,如果应用程序超过某个运行时,我希望停止所有正在运行的任务。 正在设置tokenSource.cancel(),但任务仍在运行,直到它们正常结束。我猜这是因为启动了一个在cmd/可执行文件中运行批处理的进程。我是否需要终止这个过程,我是否可以通过第三方物流完成它,或者完全不同的路线是否有益? 我读过关于thread.abort()的文章,但它似乎不受欢迎 我正在从执行ExecuteDefault的主窗口启动后台工作程序 Background worker = new BackgroundWorke

如果应用程序超过某个运行时,我希望停止所有正在运行的任务。 正在设置tokenSource.cancel(),但任务仍在运行,直到它们正常结束。我猜这是因为启动了一个在cmd/可执行文件中运行批处理的进程。我是否需要终止这个过程,我是否可以通过第三方物流完成它,或者完全不同的路线是否有益? 我读过关于thread.abort()的文章,但它似乎不受欢迎

我正在从执行ExecuteDefault的主窗口启动后台工作程序

Background worker = new BackgroundWorker();
worker.doWork += (o, ea) =>
{ ExecuteDefault(worker, tokenSource);};
在execute Default中,我从OSObject访问execute函数。所有必要的辅助任务都将在此功能中启动。现在,如果应用程序运行时间超过350000毫秒,我想取消所有任务

private void ExecuteDefault(Backgroundworker worker, CancellationTokenSource tokenSource)
{
... random stuff
OSObject.RunSystemCommands(outputPath, execPath, timeframe, tasks, worker, tokenSource);
... random stuff
Task.WaitAll(tasks.ToArray(), 350000);
tokenSource.Cancel();
}
在这里,我开始不同的过程。正在执行批处理执行(如\C logicaldisk)或exe文件(如handle.exe)

aublic static void RunSystemCommands(string outputPath, string execPath, int timeframe, List<Task> tasks, Backgroundowrker worker, CancellationTokenSource tokenSource)
{
    foreach(Command activeCommand in Commands.SystemCommands)
    {
        string keyname = activeCommmand.Name;
        if (keyname == "foo")
        {
        Task newTask = Task.Factory.Startnew(() =>
           {
           Executes.ExecuteBatch(outputFile, activeCommand)
           }, tokenSource.Token);
         tasks.Add(newTask);
        }
        else if (keyname == "bar")
        {
        ...
        }
    }
}
 public static void ExecuteBatch(string outputFile, Command command, bool parse = false)
    {
        log.DebugFormat("Executing Task: {0} | Name: {1} | Command: {2}", Task.CurrentId, command.Name, command.Execute);
        log.Info("Executing Task: " + command.Name);
        //create new process and write process start information
        Process p = new Process();

        System.Diagnostics.ProcessStartInfo startInfo = new System.Diagnostics.ProcessStartInfo();
        startInfo.WindowStyle = System.Diagnostics.ProcessWindowStyle.Hidden;
        startInfo.UseShellExecute = false;
        startInfo.FileName = @"C:\Windows\System32\cmd.exe";
        startInfo.StandardOutputEncoding = Encoding.GetEncoding(850);
        startInfo.RedirectStandardOutput = true;
        startInfo.RedirectStandardError = true;
        startInfo.CreateNoWindow = true;
        startInfo.Arguments = command.Execute;
        p.StartInfo = startInfo;

        string delimiter = new String('=', 80);
        string output = "";
        string errorOutput = "";

        log.DebugFormat("Task {0}: writing outputFile for {1}", Task.CurrentId, outputFile);
        System.IO.File.WriteAllText(outputFile, (command.Execute.Replace("/C ", "") + Environment.NewLine));
        System.IO.File.AppendAllText(outputFile, delimiter + Environment.NewLine + Environment.NewLine);


        p.ErrorDataReceived += (sender, eventArgs) => {
            errorOutput = "###Erroroutput### "+ eventArgs.Data + Environment.NewLine;

            System.IO.File.AppendAllText(outputFile, errorOutput);

        };

        p.OutputDataReceived += (sender, args) =>
        {
            if (args==null || args.Data==null || args.Data == "")
                return;

            output =args.Data+Environment.NewLine;

            if (parse == true)
            {
                output = Parser.ParseOutput(command.Name, output);
            }

            try
            {
                System.IO.File.AppendAllText(outputFile, output);
            }
            catch (Exception e)
            {

                log.Debug("Could not write to file. " + e.Message);
            }

        };

        p.Start();
        p.BeginOutputReadLine();

        p.WaitForExit(command.Timeout)

        log.DebugFormat("Task: {3} | Name: {4} | Start: {0}, End: {1}, Elapsed: {2}", p.StartTime.ToString("HH:mm:ss.fff"), DateTime.Now.ToString("HH:mm:ss.fff"), (DateTime.Now.Subtract(p.StartTime)).TotalMilliseconds, Task.CurrentId, command.Name);
    }

ExecuteBatch中有什么?它需要像示例中那样检查CancellationToken并立即发送通知。通过内核对象或取消令牌标记它应该退出的任务将不会取得任何效果,除非该任务运行良好,并定期检查对象或令牌我在ExecuteBatch函数中添加了什么。