예제 #1
0
        private void WaitUntilSandboxIsReady(Process sandbox)
        {
            var readyLineReadTask = sandbox.StandardOutput.ReadLineAsync();

            if (readyLineReadTask.Wait(settings.MaintenanceTimeLimit) && readyLineReadTask.Result == "Ready")
            {
                return;
            }

            if (!sandbox.HasExited)
            {
                throw new SandboxException($"Песочница не ответила «Ready» через {settings.MaintenanceTimeLimit.TotalSeconds} секунд после запуска, убиваю её");
            }

            if (sandbox.ExitCode != 0)
            {
                log.Warn($"Песочница не ответила «Ready», а вышла с кодом {sandbox.ExitCode}");
                var stderrReader = new AsyncReader(sandbox.StandardError, settings.OutputLimit + 1);
                var stderrData   = stderrReader.GetDataAsync().Result;
                log.Warn($"Вывод песочницы в stderr:\n{stderrData}");
                var result = GetResultForNonZeroExitCode(stderrData, sandbox.ExitCode);
                throw new SandboxException(result.Error);
            }

            throw new SandboxException("Sandbox unexpectedly exited before respond");
        }
예제 #2
0
        private void RunSolutionAndWaitUntilSandboxExit(Process sandbox, out string sandboxOutput, out string sandboxError)
        {
            sandbox.Refresh();
            var startUsedMemory = sandbox.WorkingSet64;
            var startUsedTime   = sandbox.TotalProcessorTime;
            var startTime       = DateTime.Now;

            sandbox.StandardInput.WriteLine("Run");
            sandbox.StandardInput.Flush();
            sandbox.StandardInput.WriteLineAsync(submission.Input);

            var stderrReader = new AsyncReader(sandbox.StandardError, settings.OutputLimit + 1);
            var stdoutReader = new AsyncReader(sandbox.StandardOutput, settings.OutputLimit + 1);

            while (!sandbox.HasExited &&
                   !CheckIsTimeLimitExceeded(sandbox, startTime, startUsedTime) &&
                   !CheckIsMemoryLimitExceeded(sandbox, startUsedMemory) &&
                   !CheckIsOutputLimit(stdoutReader) &&
                   !CheckIsOutputLimit(stderrReader))
            {
            }

            if (!hasTimeLimit && !hasMemoryLimit && !hasOutputLimit)
            {
                /* Read all data to the end of streams */
                sandboxError   = stderrReader.GetDataAsync().Result;
                sandboxOutput  = stdoutReader.GetDataAsync().Result;
                hasOutputLimit = CheckIsOutputLimit(stdoutReader);
                hasOutputLimit = CheckIsOutputLimit(stderrReader);
            }
            else
            {
                sandboxError  = "";
                sandboxOutput = "";
            }
        }