Перенос.

This commit is contained in:
2023-09-17 22:13:42 +03:00
parent dd2e0ca7e0
commit 629d8b8477
1239 changed files with 61161 additions and 1 deletions

View File

@@ -0,0 +1,42 @@
package GlobalData.Tasks.Supervisor.Local.Linux;
import Common.Utils.Utils;
import GlobalData.Makefile.Makefile;
import GlobalData.Tasks.CompilationTask.CompilationTask;
import GlobalData.Tasks.TaskState;
import org.apache.commons.io.FileUtils;
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
public class LinuxLocalCompilationSupervisor extends LinuxLocalTaskSupervisor<CompilationTask> {
@Override
protected void PrepareWorkspace() throws Exception {
//возможно тут сделать отличие. не удалять все, а тоже сверять по дате и именам..
super.PrepareWorkspace();
Utils.CheckAndCleanDirectory(getProjectCopy());
//скопировать проект в папку. без бд.
project.Clone(getProjectCopy(), false);
//-удалить старый бинарник если есть? бессмысленно если папка и так полностью пересоздается при каждой компиляции.
//по идее надо исправить на синхронизацию.
//if (!task.binary_name.isEmpty()) {
// File old_binary = Paths.get(getProjectCopy().getAbsolutePath(), task.binary_name).toFile();
// FileUtils.forceDelete(old_binary);
// }
//создать мейкфайл.
Makefile makefile = task.getMakefile();
File makefile_text = Paths.get(getProjectCopy().getAbsolutePath(), "Makefile").toFile();
FileUtils.write(makefile_text, makefile.Generate(project));
}
@Override
protected void ValidateTaskResults() throws Exception {
if (getBinary().exists()) {
File renamed_binary = Paths.get(getProjectCopy().getAbsolutePath(),
Utils.getDateName("spf")).toFile();
task.binary_name = renamed_binary.getName();
Files.move(getBinary().toPath(), renamed_binary.toPath(), StandardCopyOption.REPLACE_EXISTING);
task.state = TaskState.Done;
} else task.state = TaskState.DoneWithErrors;
task.AnalyzeResultsTexts(project);
}
}

View File

@@ -0,0 +1,32 @@
package GlobalData.Tasks.Supervisor.Local.Linux;
import Common.Current;
import GlobalData.Tasks.RunTask.RunTask;
import java.util.Map;
public class LinuxLocalRunSupervisor extends LinuxLocalTaskSupervisor<RunTask> {
@Override
protected void PrepareWorkspace() throws Exception {
super.PrepareWorkspace();
PrepareRunTaskWorkspace(task);
}
@Override
protected void AchieveResults() throws Exception {
super.AchieveResults();
AchieveRunTaskResults(task);
}
@Override
protected Map<String, String> getEnvs() {
return Current.getRunConfiguration().getEnvMap();
}
@Override
protected String getScriptText() {
return "ulimit -s unlimited\n" + super.getScriptText();
}
@Override
protected void ValidateTaskResults() throws Exception {
task.AnalyzeResultsTexts(project);
}
protected String getCoupDeGrace() {
return "killall -SIGKILL " + task.getCompilationTask().binary_name;
}
}

View File

@@ -0,0 +1,82 @@
package GlobalData.Tasks.Supervisor.Local.Linux;
import Common.Utils.Utils;
import GlobalData.Tasks.Supervisor.Local.LocalTaskSupervisor;
import GlobalData.Tasks.Task;
import GlobalData.Tasks.TaskState;
import GlobalData.User.User;
import ProjectData.Project.db_project_info;
import Visual_DVM_2021.Passes.PassException;
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.util.Date;
public abstract class LinuxLocalTaskSupervisor<T extends Task> extends LocalTaskSupervisor<T> {
@Override
protected void StartTask() throws Exception {
super.StartTask();
task.PID = Utils.readLine(taskProcess);
}
@Override
protected String getScriptText() {
User user = task.getUser();
return
String.join(" ",
Utils.DQuotes(user.getStarterFile()),
Utils.DQuotes(user.getLauncherFile()),
String.valueOf(task.maxtime),
Utils.DQuotes(getCoupDeGrace()),
task.getFullCommand()
);
}
@Override
protected void CheckTask() throws Exception {
if (getDONE_file().exists())
task.state = TaskState.Finished;
else if (getTIMEOUT_file().exists())
task.state = TaskState.AbortedByTimeout;
}
@Override
protected String getKillCommand() {
return "kill -2 " + task.PID;
}
@Override
public void WaitForTask() throws Exception {
if (isTaskActive()) {
if (task.PID.isEmpty())
throw new PassException("Ошибка при старте : идентификатор задачи не определен.");
task.StartDate = (new Date()).getTime();
pass.ShowMessage1("Задача активна, идентификатор " + Utils.Brackets(task.PID));
RefreshProgress();
do {
Thread.sleep(getTaskCheckPeriod() * 1000L);
performanceTime += getTaskCheckPeriod();
CheckTask();
if (isTaskActive()) CheckIfNeedAbort();
RefreshProgress();
} while (isTaskActive());
}
}
protected File getProjectTime() {
return Paths.get(getProjectCopy().getAbsolutePath(), db_project_info.time_file).toFile();
}
protected File getDONE_file() {
return Paths.get(getProjectCopy().getAbsolutePath(), db_project_info.DONE).toFile();
}
protected File getTIMEOUT_file() {
return Paths.get(getProjectCopy().getAbsolutePath(), db_project_info.TIMEOUT).toFile();
}
@Override
protected void PrepareWorkspace() throws Exception {
super.PrepareWorkspace();
Utils.forceDeleteWithCheck(getDONE_file());
Utils.forceDeleteWithCheck(getTIMEOUT_file());
Utils.forceDeleteWithCheck(getProjectTime());
}
@Override
protected void CalculatePerformanceTime() throws Exception {
Files.move(getProjectTime().toPath(), task.getTimeFile().toPath(), StandardCopyOption.REPLACE_EXISTING);
task.RefreshTime();
}
}

View File

@@ -0,0 +1,105 @@
package GlobalData.Tasks.Supervisor.Local;
import Common.Global;
import Common.Utils.Utils;
import GlobalData.Tasks.RunTask.RunTask;
import GlobalData.Tasks.Supervisor.TaskSupervisor;
import GlobalData.Tasks.Task;
import GlobalData.Tasks.TaskState;
import ProjectData.Project.db_project_info;
import Visual_DVM_2021.Passes.Pass_2021;
import org.apache.commons.io.FileUtils;
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
import java.util.Map;
import java.util.Vector;
//про mpi mpich2
//https://stackoverflow.com/questions/12983635/how-to-include-library-mpich2-in-mingw
public abstract class LocalTaskSupervisor<T extends Task> extends TaskSupervisor<T, Pass_2021> {
protected Process taskProcess;
protected int exitCode;
@Override
protected void StartTask() throws Exception {
exitCode = Utils.Nan;
taskProcess = Utils.startScript(task.getLocalWorkspace(), getProjectCopy(), "start_task_script", getScriptText(), getEnvs());
task.state = TaskState.Running;
}
@Override
protected void AbortTask() throws Exception {
Process killer = Runtime.getRuntime().exec(getKillCommand());
killer.waitFor();
}
//---->
protected abstract String getScriptText();
protected abstract String getKillCommand();
//----->
protected Map<String, String> getEnvs() {
return null;
}
//---->
protected File getProjectCopy() {
return Paths.get(task.getUser().getLocalProjectsDir().getAbsolutePath(), project.getUniqKey()).toFile();
}
protected File getBinary() {
return Paths.get(getProjectCopy().getAbsolutePath(), "0" + (Global.isWindows ? ".exe" : "")).toFile();
}
protected File getProjectOutput() {
return Paths.get(getProjectCopy().getAbsolutePath(), db_project_info.out_file).toFile();
}
protected File getProjectErrors() {
return Paths.get(getProjectCopy().getAbsolutePath(), db_project_info.err_file).toFile();
}
@Override
protected void PrepareWorkspace() throws Exception {
super.PrepareWorkspace(); //локальная подготовка
Utils.forceDeleteWithCheck(getProjectOutput());
Utils.forceDeleteWithCheck(getProjectErrors());
}
@Override
protected void AchieveResults() throws Exception {
Files.copy(getProjectOutput().toPath(), task.getOutputFile().toPath(), StandardCopyOption.REPLACE_EXISTING);
Files.copy(getProjectErrors().toPath(), task.getErrorsFile().toPath(), StandardCopyOption.REPLACE_EXISTING);
}
protected void AchieveRunTaskResults(RunTask rTask) throws Exception {
rTask.parseCleanTime();
//-статистика
Vector<File> stsFiles = new Vector<>();
Utils.getFilesByExtensions_r(getProjectCopy(), stsFiles, "gz+");
if (stsFiles.size() > 0) {
File file = stsFiles.get(0);
rTask.UpdateLastStsName(file.getName());
Files.copy(file.toPath(), rTask.getLocalStsFile().toPath(), StandardCopyOption.REPLACE_EXISTING);
rTask.hasDvmSts = true;
}
/*
//-gcov
if (rTask.getRunConfiguration().needsGCOV()) {
//-
Process gcovProcess = Utils.startScript(rTask.getLocalWorkspace(), getProjectCopy(), "gcov_script", "gcov *.gcda -p");
gcovProcess.waitFor();
//-
project.CreateGCOVDirs();
Vector<File> gcovs = new Vector<>();
Utils.getFilesByExtensions_r(getProjectCopy(), gcovs, "gcov");
for (File src : gcovs) {
File dst = Paths.get(project.getGCOVDirectory().getAbsolutePath(),
src.getName().replace("#",
Global.isWindows ? "\\" : "/")).toFile();
Files.move(src.toPath(), dst.toPath(), StandardCopyOption.REPLACE_EXISTING);
}
}
*/
}
protected void PrepareRunTaskWorkspace(RunTask rTask) throws Exception {
Utils.deleteFilesByExtensions(getProjectCopy(), "gcda", "gcov", "gz+", "par");
rTask.UpdateLastStsName("");
//отправить usr.par.
if (rTask.hasDVMPar()) {
File par_text = Paths.get(getProjectCopy().getAbsolutePath(), "usr.par").toFile();
FileUtils.write(par_text, String.join("\n", rTask.getRunConfiguration().getParList()));
}
}
protected String getCoupDeGrace(){return "";}
}

View File

@@ -0,0 +1,54 @@
package GlobalData.Tasks.Supervisor.Local.Windows;
import Common.Global;
import Common.Utils.Utils;
import GlobalData.Makefile.Makefile;
import GlobalData.Settings.SettingName;
import GlobalData.Tasks.CompilationTask.CompilationTask;
import GlobalData.Tasks.TaskState;
import org.apache.commons.io.FileUtils;
import java.io.File;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;
public class WindowsLocalCompilationSupervisor extends WindowsLocalTaskSupervisor<CompilationTask> {
@Override
protected String getKillCommand() {
return "taskkill /FI \"IMAGENAME eq make.exe\" /F /T";
}
@Override
protected String getScriptText() {
return Utils.DQuotes(Global.db.settings.get(SettingName.LocalMakePathWindows).Value) + " 1>out.txt 2>err.txt";
}
//скорее всего как то выделить подготовку к компиляции как метод предка.
@Override
protected void PrepareWorkspace() throws Exception {
//возможно тут сделать отличие. не удалять все, а тоже сверять по дате и именам..
super.PrepareWorkspace();
Utils.CheckAndCleanDirectory(getProjectCopy());
//скопировать проект в папку. без бд.
project.Clone(getProjectCopy(), false);
//-удалить старый бинарник если есть? бессмысленно если папка и так полностью пересоздается при каждой компиляции.
//по идее надо исправить на синхронизацию.
//if (!task.binary_name.isEmpty()) {
// File old_binary = Paths.get(getProjectCopy().getAbsolutePath(), task.binary_name).toFile();
// FileUtils.forceDelete(old_binary);
// }
//создать мейкфайл.
Makefile makefile = task.getMakefile();
File makefile_text = Paths.get(getProjectCopy().getAbsolutePath(), "Makefile").toFile();
FileUtils.write(makefile_text, makefile.Generate(project));
}
//как и валидация.
@Override
protected void ValidateTaskResults() throws Exception {
if (getBinary().exists()) {
File renamed_binary = Paths.get(getProjectCopy().getAbsolutePath(),
Utils.getDateName("spf") + ".exe").toFile();
task.binary_name = renamed_binary.getName();
Files.move(getBinary().toPath(), renamed_binary.toPath(), StandardCopyOption.REPLACE_EXISTING);
task.state = TaskState.Done;
} else task.state = TaskState.DoneWithErrors;
task.AnalyzeResultsTexts(project);
}
}

View File

@@ -0,0 +1,48 @@
package GlobalData.Tasks.Supervisor.Local.Windows;
import Common.Current;
import GlobalData.Tasks.RunTask.RunTask;
import java.util.Map;
public class WindowsLocalRunSupervisor extends WindowsLocalTaskSupervisor<RunTask> {
@Override
protected void ValidateTaskResults() throws Exception {
task.AnalyzeResultsTexts(project);
}
@Override
protected String getScriptText() {
return task.getFullCommand() + " 1>out.txt 2>err.txt";
}
//общая часть для запуска.
@Override
protected void PrepareWorkspace() throws Exception {
super.PrepareWorkspace();
PrepareRunTaskWorkspace(task);
}
@Override
protected void AchieveResults() throws Exception {
super.AchieveResults();
AchieveRunTaskResults(task);
}
@Override
protected Map<String, String> getEnvs() {
return Current.getRunConfiguration().getEnvMap();
}
void kill_mpi() throws Exception {
System.out.println("KILLING MPI");
}
@Override
protected void AbortTask() throws Exception {
super.AbortTask(); //убить группу.
kill_mpi();
}
@Override
protected String getKillCommand() {
return "taskkill /FI \"IMAGENAME eq " + task.getCompilationTask().binary_name + "\" /F /T";
}
/*
@Override
protected void CoupDeGraceTask() throws Exception {
kill_mpi();
}
*/
}

View File

@@ -0,0 +1,51 @@
package GlobalData.Tasks.Supervisor.Local.Windows;
import Common.Global;
import GlobalData.Tasks.Supervisor.Local.LocalTaskSupervisor;
import GlobalData.Tasks.Task;
import GlobalData.Tasks.TaskState;
import java.util.Date;
import java.util.concurrent.TimeUnit;
//https://ab57.ru/cmdlist/taskkill.html
public abstract class WindowsLocalTaskSupervisor<T extends Task> extends LocalTaskSupervisor<T> {
@Override
protected void StartTask() throws Exception {
super.StartTask();
task.PID = "start_task_script.bat"; // возможно делать уникальное имя скрипта, чтобы было чем убивать под виндой.
}
//--------------------------------------------------->>>
protected void CheckIfNeedAbort() {
if (project.getInterruptFile().exists())
task.state = TaskState.AbortingByUser;
if (performanceTime > task.maxtime) {
try {
AbortTask();
} catch (Exception ex) {
Global.Log.PrintException(ex);
}
task.state = TaskState.AbortedByTimeout;
}
}
@Override
protected void CheckTask() throws Exception {
if (taskProcess.waitFor(getTaskCheckPeriod(), TimeUnit.SECONDS)) {
exitCode = taskProcess.waitFor();
task.state = TaskState.Finished;
} else {
performanceTime += getTaskCheckPeriod();
}
}
@Override
public void WaitForTask() throws Exception {
if (isTaskActive()) {
task.StartDate = (new Date()).getTime();
pass.ShowMessage1("Задача активна");
RefreshProgress();
do {
CheckTask();
if (isTaskActive()) CheckIfNeedAbort();
RefreshProgress();
} while (isTaskActive());
}
}
}

View File

@@ -0,0 +1,58 @@
package GlobalData.Tasks.Supervisor.Remote;
import Common.Current;
import Common.Utils.Utils;
import GlobalData.RemoteFile.RemoteFile;
import GlobalData.Tasks.QueueSystem.MVS;
import GlobalData.Tasks.TaskState;
public class MVSRunSupervisor extends ServerRunSupervisor {
MVS mvs = new MVS();
int mvs_time;
@Override
protected RemoteFile getRemoteOutput() {
return new RemoteFile(getRemoteProject().full_name + "/" + task.PID, "output");
}
@Override
protected RemoteFile getRemoteErrors() {
return new RemoteFile(getRemoteProject().full_name + "/" + task.PID, "errors");
}
@Override
protected String getLaunchScriptText() {
return task.getFullCommand();
}
@Override
protected int getTaskCheckPeriod() {
return 5;
}
@Override
public int getMaxtime() {
return mvs_time * 60;
}
@Override
protected void StartTask() throws Exception {
String env = String.join(" ", Current.getRunConfiguration().getEnvList());
mvs_time = (task.maxtime / 60); //в минутах
if (task.maxtime % 60 > 0) mvs_time += 1;
String res = "maxtime=" + Utils.DQuotes(mvs_time) + " ./run";
if (!env.isEmpty())
res = env + " " + res;
mvs.enqueueTask(pass.ShellCommand(
"cd " + Utils.DQuotes(getRemoteProject().full_name),
res), task);
}
@Override
protected boolean isTaskActive() {
return super.isTaskActive() || task.state.equals(TaskState.Queued);
}
@Override
protected void CheckTask() throws Exception {
mvs.checkTask(pass.ShellCommand(mvs.getCheckTaskCommand(task)), task);
}
@Override
protected void AbortTask() throws Exception {
pass.ShellCommand(mvs.getCancelTaskCommand(task));
}
@Override
protected void CalculatePerformanceTime() throws Exception {
task.Time = performanceTime;
}
}

View File

@@ -0,0 +1,48 @@
package GlobalData.Tasks.Supervisor.Remote;
import Common.Utils.Utils;
import GlobalData.Makefile.Makefile;
import GlobalData.RemoteFile.RemoteFile;
import GlobalData.Tasks.CompilationTask.CompilationTask;
import GlobalData.Tasks.TaskState;
import java.io.File;
public class RemoteCompilationSupervisor extends RemoteTaskSupervisor<CompilationTask> {
@Override
protected void PrepareWorkspace() throws Exception {
//0. если нет папки с его именем создаем.
pass.tryMKDir(getRemoteProject());
pass.SynchronizeProjectSubDirsR(project, project.Home, getRemoteProject(), false);
pass.tryRM(getBinary());
if (!task.binary_name.isEmpty()) {
RemoteFile old_binary = new RemoteFile(getRemoteProject().full_name, task.binary_name);
pass.tryRM(old_binary);
}
//отправить мейкфайл.
Makefile makefile = task.getMakefile();
File makefile_text = Utils.CreateTempFile("makefile", makefile.Generate(project));
pass.putSingleFile(makefile_text, new RemoteFile(getRemoteProject().full_name, "Makefile"));
//очистить все что связано с gcov
//файлы gcda, gcno, gcov
pass.deleteFilesByExtensions(getRemoteProject(), "gcda", "gcno", "gcov");
//очистить служебные файлы.
super.PrepareWorkspace();
}
@Override
protected void StartTask() throws Exception {
//UI.Info("starting task");
task.PID = pass.ShellCommand(
"cd " + Utils.DQuotes(getRemoteProject().full_name),
getStartCommand());
task.state = TaskState.Running;
}
@Override
protected void ValidateTaskResults() throws Exception {
if (pass.Exists(getRemoteProject().full_name, getBinary().name)) {
RemoteFile renamed_binary = new RemoteFile(getRemoteProject().full_name, Utils.getDateName("spf_" + getBinary().name));
pass.sftpChannel.rename(getBinary().full_name, renamed_binary.full_name);
task.binary_name = renamed_binary.name;
task.state = TaskState.Done;
} else task.state = TaskState.DoneWithErrors;
task.AnalyzeResultsTexts(project);
}
}

View File

@@ -0,0 +1,76 @@
package GlobalData.Tasks.Supervisor.Remote;
import Common.Utils.Utils;
import GlobalData.RemoteFile.RemoteFile;
import GlobalData.Tasks.Supervisor.TaskSupervisor;
import GlobalData.Tasks.Task;
import GlobalData.Tasks.TaskState;
import ProjectData.Project.db_project_info;
import Visual_DVM_2021.Passes.SSH.ConnectionPass;
public abstract class RemoteTaskSupervisor<T extends Task> extends TaskSupervisor<T, ConnectionPass> {
protected RemoteFile getRemoteProjectsPath() {
return new RemoteFile(pass.user.getRemoteProjectsPath(), true);
}
protected RemoteFile getRemoteProject() {
return new RemoteFile(getRemoteProjectsPath().full_name, project.getUniqKey(), true);
}
protected RemoteFile getBinary() {
return new RemoteFile(getRemoteProject().full_name, "0");
}
protected RemoteFile getRemoteTime() {
return new RemoteFile(getRemoteProject().full_name, db_project_info.time_file);
}
protected RemoteFile getRemoteOutput() {
return new RemoteFile(getRemoteProject().full_name, db_project_info.out_file);
}
protected RemoteFile getRemoteErrors() {
return new RemoteFile(getRemoteProject().full_name, db_project_info.err_file);
}
public RemoteFile getDONE_file() {
return new RemoteFile(getRemoteProject().full_name, db_project_info.DONE);
}
public RemoteFile getTIMEOUT_file() {
return new RemoteFile(getRemoteProject().full_name, db_project_info.TIMEOUT);
}
@Override
protected void PrepareWorkspace() throws Exception {
super.PrepareWorkspace(); //локальная подготовка
pass.tryRM(getDONE_file());
pass.tryRM(getTIMEOUT_file());
pass.tryRM(getRemoteOutput());
pass.tryRM(getRemoteErrors());
pass.tryRM(getRemoteTime());
}
@Override
protected void CheckTask() throws Exception {
if (pass.Exists(getRemoteProject().full_name, db_project_info.DONE))
task.state = TaskState.Finished;
else if (pass.Exists(getRemoteProject().full_name, db_project_info.TIMEOUT))
task.state = TaskState.AbortedByTimeout;
}
@Override
protected void AchieveResults() throws Exception {
pass.tryGetSingleFile(getRemoteOutput(), task.getOutputFile(), 10240);
pass.tryGetSingleFile(getRemoteErrors(), task.getErrorsFile(), 10240);
}
@Override
protected void AbortTask() throws Exception {
pass.ShellCommand("kill -2 " + task.PID);
}
@Override
protected void CalculatePerformanceTime() throws Exception {
if (pass.tryGetSingleFile(getRemoteTime(), task.getTimeFile(), 0))
task.RefreshTime();
}
protected String getStartCommand() {
String res =
String.join(" ",
Utils.DQuotes(pass.getStarter()),
Utils.DQuotes(pass.getLauncher()),
String.valueOf(task.maxtime),
Utils.DQuotes(getCoupDeGrace()),
task.getFullCommand()
);
System.out.println(res);
return res;
}
}

View File

@@ -0,0 +1,91 @@
package GlobalData.Tasks.Supervisor.Remote;
import Common.Current;
import Common.Utils.Utils;
import GlobalData.RemoteFile.RemoteFile;
import GlobalData.Tasks.RunTask.RunTask;
import GlobalData.Tasks.TaskState;
import com.jcraft.jsch.ChannelSftp;
import java.io.ByteArrayInputStream;
import java.io.File;
import java.nio.charset.StandardCharsets;
import java.util.Vector;
public class ServerRunSupervisor extends RemoteTaskSupervisor<RunTask> {
@Override
protected void StartTask() throws Exception {
String res = "./run";
String env = String.join(" ", Current.getRunConfiguration().getEnvList());
if (!env.isEmpty()) res = env + " " + res;
task.PID = pass.ShellCommand(
"cd " + Utils.DQuotes(getRemoteProject().full_name),
"ulimit -s unlimited",
res);
task.state = TaskState.Running;
}
@Override
protected void ValidateTaskResults() throws Exception {
task.AnalyzeResultsTexts(project);
}
@Override
protected void PrepareWorkspace() throws Exception {
super.PrepareWorkspace();
//-------------------------
//удалить старую статистику если оная есть.
if (!task.last_sts_name.isEmpty()) {
pass.tryRM(new RemoteFile(getRemoteProject().full_name, task.last_sts_name));
task.UpdateLastStsName("");
}
//-------------------------
String launchScriptText = getLaunchScriptText();
RemoteFile launchScript = new RemoteFile(getRemoteProject().full_name, "run");
pass.sftpChannel.put(
new ByteArrayInputStream(
launchScriptText.getBytes(StandardCharsets.UTF_8)), launchScript.full_name);
pass.sftpChannel.chmod(0777, launchScript.full_name);
//-
//отправить usr.par.
if (task.hasDVMPar()) {
File par_text = Utils.CreateTempFile("usr", String.join("\n", task.getRunConfiguration().getParList()));
pass.putSingleFile(par_text, new RemoteFile(getRemoteProject().full_name, "usr.par"));
}
}
protected String getLaunchScriptText() {
return getStartCommand();
}
@Override
protected String getCoupDeGrace() {
return "killall -SIGKILL " + task.getCompilationTask().binary_name;
}
@Override
protected void AchieveResults() throws Exception {
super.AchieveResults();
task.parseCleanTime();
//теперь ищем статистику.
//статистика
Vector<ChannelSftp.LsEntry> files = pass.sftpChannel.ls(getRemoteProject().full_name);
for (ChannelSftp.LsEntry file : files) {
if (file.getFilename().endsWith("sts.gz+")) {
task.UpdateLastStsName(file.getFilename());
break;
}
}
if (!task.last_sts_name.isEmpty()) {
RemoteFile remote_sts = new RemoteFile(getRemoteProject().full_name, task.last_sts_name);
task.hasDvmSts = pass.tryGetSingleFile(remote_sts, task.getLocalStsFile(), 10240);
}
}
}
/*
//ищем GCOV
if (task.getRunConfiguration().needsGCOV()) {
pass.ShellCommand("cd " + Utils.DQuotes(getRemoteProject().full_name),
"gcov *.gcda -p"
);
project.CreateGCOVDirs();
Vector<RemoteFile> gcov_results = pass.getFilesByExtensions(getRemoteProject(), "gcov");
for (RemoteFile gcov_file : gcov_results) {
File local_gcov = Paths.get(project.getGCOVDirectory().getAbsolutePath(),
gcov_file.name.replace("#", "\\")).toFile();
pass.getSingleFile(gcov_file.full_name, local_gcov.getAbsolutePath());
}
*/

View File

@@ -0,0 +1,138 @@
package GlobalData.Tasks.Supervisor;
import Common.Global;
import Common.Utils.Utils;
import GlobalData.Tasks.Task;
import GlobalData.Tasks.TaskState;
import ProjectData.Project.db_project_info;
import Visual_DVM_2021.Passes.PassException;
import Visual_DVM_2021.Passes.Pass_2021;
import java.util.Date;
public abstract class TaskSupervisor<T extends Task, P extends Pass_2021> {
public T task; //задача
protected db_project_info project; //проект к которому относится задача
protected P pass; //проход отвечающий за задачу
protected int performanceTime; //сколько задача уже выполняется.
public void ShowTaskState(){
Global.db.tables.get(task.getClass()).ShowUI(task.getPK());
}
public void Init(T task_in, P pass_in, db_project_info project_in) {
task = task_in;
pass = pass_in;
project = project_in;
try {
project.CleanInterruptFile();
} catch (Exception ex) {
Global.Log.PrintException(ex);
}
}
protected void PrepareWorkspace() throws Exception {
Utils.CheckAndCleanDirectory(task.getLocalWorkspace());
}
protected abstract void StartTask() throws Exception;
protected boolean isTaskActive() {
return task.state.equals(TaskState.Running);
}
//периодичность проверки состояния задачи (с)
protected int getTaskCheckPeriod() {
return 1;
}
public int getMaxtime() {
return task.maxtime;
}
protected void RefreshProgress() {
pass.ShowProgress2(getMaxtime(), performanceTime, task.state.getDescription() + ", прошло секунд");
}
//проверка состояния задачи
protected void CheckTask() throws Exception {
}
protected void CheckIfNeedAbort() {
if (project.getInterruptFile().exists()){
task.state = TaskState.AbortingByUser;
ShowTaskState();
}
}
//досрочное прерывание задачи
protected void AbortTask() throws Exception {
}
protected String getCoupDeGrace(){
return "";
}
//добивание задачи после ее завершения по таймауту. не всегда нужно
// protected void CoupDeGraceTask() throws Exception {}
//получить результаты выполнения задачи. в случае локальной машины, очевидно, пустая функция
protected void AchieveResults() throws Exception {
}
protected abstract void ValidateTaskResults() throws Exception;
//получить время выполнения задачи. по умолчанию самый грубый метод.
protected void CalculatePerformanceTime() throws Exception {
task.Time = performanceTime;
}
//рабочий цикл задачи.
public void PerformTask() throws Exception {
if (task.hasProgress())
pass.ShowProgressTextOnly(task.progressAll, task.progressStep, "задача");
//сброс
performanceTime = 0;
System.out.println(performanceTime);
task.Reset();
ShowTaskState();
pass.ShowMessage1("Подготовка рабочего пространства задачи..");
PrepareWorkspace();
ShowTaskState();
pass.ShowMessage1("Старт задачи..");
//запуск задачи
StartTask();
ShowTaskState();
WaitForTask();
//маловероятно, но в теории задача может оказаться выполненной сразу после команды выполнения
//например если запуск шел через систему очередей.
//анализируем состояние.
//если приказано убить задачу. убиваем.
if (task.state == TaskState.AbortingByUser) {
pass.ShowMessage1("Принудительная остановка задачи..");
AbortTask();
task.state = TaskState.AbortedByUser;
ShowTaskState();
}
pass.ShowMessage1("Задача " + Utils.Brackets(task.state.getDescription()));
task.EndDate = (new Date()).getTime();
pass.ShowMessage2("Получение результатов");
AchieveResults();
pass.ShowMessage2("Анализ результатов");
switch (task.state) {
case Finished:
ValidateTaskResults();
CalculatePerformanceTime();
break;
case AbortedByTimeout:
task.MaximizeTime();
pass.ShowMessage2("Добивание задачи..");
break;
default:
break;
}
}
public void WaitForTask() throws Exception {
if (isTaskActive()) {
if (task.PID.isEmpty())
throw new PassException("Ошибка при старте : идентификатор задачи не определен.");
task.StartDate = (new Date()).getTime();
pass.ShowMessage1("Задача активна, идентификатор " + Utils.Brackets(task.PID));
RefreshProgress();
do {
Thread.sleep(getTaskCheckPeriod() * 1000);
performanceTime += getTaskCheckPeriod();
CheckTask();
if (isTaskActive()) CheckIfNeedAbort();
RefreshProgress();
} while (isTaskActive());
ShowTaskState();
}
}
public void UpdateTask() throws Exception {
Global.db.Update(task);
}
}