/// <summary> /// Compile source code /// </summary> public string CompileCode(Compiler Compiler) { //apply for temp directory and compile code //apply for temp directory if (!Directory.Exists(Path.GetTempPath() + @"SOCJTemp")) Directory.CreateDirectory(Path.GetTempPath() + @"SOCJTemp"); var codeFilename = Path.GetTempPath() + @"SOCJTemp\" + Path.GetRandomFileName() + "." + JudgerManager.LanguageExtensions[Unit.Language]; var programFilename = Path.GetTempPath() + @"SOCJTemp\" + Path.GetRandomFileName() + ".exe"; File.WriteAllText(codeFilename, Unit.Code); if (File.Exists(programFilename)) File.Delete(programFilename); //compile code var compilerProcess = new Process(); compilerProcess.StartInfo.FileName = Compiler.Filename; compilerProcess.StartInfo.Arguments = Compiler.Argument.Replace(@"{Filename}", codeFilename).Replace(@"{Output}", programFilename); compilerProcess.StartInfo.UseShellExecute = false; compilerProcess.StartInfo.CreateNoWindow = true; compilerProcess.Start(); compilerProcess.WaitForExit(); File.Delete(codeFilename); return programFilename; }
/// <summary> /// Start Judging with given compiler /// </summary> /// <param name="Compiler">Compiler used to compile the code</param> public void StartJudging(Compiler Compiler, bool WaitForExit) { var programFilename = CompileCode(Compiler); //no compiled file means compile failed if (!File.Exists(programFilename)) { //compilation finished OnCompiled?.Invoke(this, new CompilationFinishedEventArgs() { IsCompilationSucceeded = false }); Results = new List<JudgeResult>(new JudgeResult[] { new JudgeResult() { Result = JudgeResultEnum.CompileError } }); return; } else { OnCompiled?.Invoke(this, new CompilationFinishedEventArgs() { IsCompilationSucceeded = true }); } //run if compilation successful //initialize taskfactory judgingTasks = new TaskFactory(); cts = new CancellationTokenSource(); Task[] tasks = new Task[Data.Datas.Count]; //run each sample data Data.Datas.ForEach(d => { tasks[Data.Datas.IndexOf(d)] = (judgingTasks.StartNew(() => { TestProgram(programFilename, d, WaitForExit); }, cts.Token).ContinueWith((r) => { OnJudged?.Invoke(this, new JudgementFinishedEventArgs() { Index = Data.Datas.IndexOf(d) }); })); }); //binding event notification judgingTasks.ContinueWhenAll(tasks, (t) => { File.Delete(programFilename); OnJudgedAll?.Invoke(); }); }