aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorThomas White <taw@physics.org>2021-02-18 11:22:13 +0100
committerThomas White <taw@physics.org>2021-02-18 11:22:13 +0100
commita9584e4fd46cad8bb88d31629e9b9a31ce8e46f8 (patch)
treeec8f77cc157f7e79ae6f70db97196425f0b20ddb /src
parent240f9e7311497c15386d0b62242f6747a24ac7bc (diff)
SLURM: Submit merging and ambigator jobs via script
Diffstat (limited to 'src')
-rw-r--r--src/gui_ambi.c2
-rw-r--r--src/gui_backend_slurm.c204
-rw-r--r--src/gui_merge.c183
-rw-r--r--src/gui_merge.h4
4 files changed, 151 insertions, 242 deletions
diff --git a/src/gui_ambi.c b/src/gui_ambi.c
index 9050eb5c..d29ce6b0 100644
--- a/src/gui_ambi.c
+++ b/src/gui_ambi.c
@@ -476,6 +476,8 @@ int write_ambigator_script(const char *filename,
fh = fopen(filename, "w");
if ( fh == NULL ) return 1;
+ fprintf(fh, "#!/bin/sh\n");
+
fprintf(fh, "cat \\\n");
for ( i=0; i<input->n_streams; i++ ) {
fprintf(fh, "%s \\\n", input->streams[i]);
diff --git a/src/gui_backend_slurm.c b/src/gui_backend_slurm.c
index c8572d5d..c75d6ab8 100644
--- a/src/gui_backend_slurm.c
+++ b/src/gui_backend_slurm.c
@@ -318,6 +318,73 @@ static uint32_t submit_batch_job(const char *geom_filename,
}
+/* For submitting a single script to the SLURM cluster.
+ * Used for merging and ambigator, but not for indexing - that needs something
+ * more sophisticated. */
+static struct slurm_job *start_slurm_job(enum slurm_job_type type,
+ const char *script_filename,
+ const char *jobname,
+ const char *workdir,
+ const char *partition,
+ const char *email_address)
+{
+ char **env;
+ int n_env;
+ char *script;
+ struct slurm_job *job;
+ job_desc_msg_t job_desc_msg;
+ submit_response_msg_t *resp;
+ int r;
+
+ script = load_entire_file(script_filename);
+ if ( script == NULL ) return NULL;
+
+ job = malloc(sizeof(struct slurm_job));
+ if ( job == NULL ) return NULL;
+
+ job->type = type;
+
+ env = create_env(&n_env, NULL);
+
+ slurm_init_job_desc_msg(&job_desc_msg);
+ job_desc_msg.user_id = getuid();
+ job_desc_msg.group_id = getgid();
+ job_desc_msg.mail_user = safe_strdup(email_address);
+ job_desc_msg.mail_type = MAIL_JOB_FAIL;
+ job_desc_msg.comment = "Submitted via CrystFEL GUI";
+ job_desc_msg.shared = 0;
+ job_desc_msg.time_limit = 60;
+ job_desc_msg.partition = safe_strdup(partition);
+ job_desc_msg.min_nodes = 1;
+ job_desc_msg.max_nodes = 1;
+ job_desc_msg.name = safe_strdup(jobname);
+ job_desc_msg.std_err = strdup("stderr.log");
+ job_desc_msg.std_out = strdup("stdout.log");
+ job_desc_msg.work_dir = strdup(workdir);
+ job_desc_msg.script = script;
+ job_desc_msg.environment = env;
+ job_desc_msg.env_size = n_env;
+
+ r = slurm_submit_batch_job(&job_desc_msg, &resp);
+ if ( r ) {
+ ERROR("Couldn't submit job: %i\n", errno);
+ return NULL;
+ }
+
+ free(job_desc_msg.mail_user);
+ free(job_desc_msg.partition);
+ free(job_desc_msg.name);
+ free(job_desc_msg.work_dir);
+ free(job_desc_msg.std_err);
+ free(job_desc_msg.std_out);
+
+ job->job_id = resp->job_id;
+ slurm_free_submit_response_response_msg(resp);
+
+ return job;
+}
+
+
static void write_partial_file_list(GFile *workdir,
const char *list_filename,
int j,
@@ -694,7 +761,49 @@ static void *run_ambi(const char *job_title,
struct gui_indexing_result *input,
void *opts_priv)
{
- return NULL;
+ struct slurm_job *job;
+ struct slurm_ambi_opts *opts = opts_priv;
+ GFile *workdir;
+ GFile *sc_gfile;
+ char *sc_filename;
+ GFile *stream_gfile;
+ char *stream_str;
+
+ workdir = make_job_folder(job_title, job_notes);
+ if ( workdir == NULL ) return NULL;
+
+ stream_gfile = g_file_get_child(workdir, "ambi.stream");
+ stream_str = g_file_get_path(stream_gfile);
+ g_object_unref(stream_gfile);
+
+ sc_gfile = g_file_get_child(workdir, "run_ambigator.sh");
+ sc_filename = g_file_get_path(sc_gfile);
+ g_object_unref(sc_gfile);
+ if ( sc_filename == NULL ) return NULL;
+
+ if ( !write_merge_script(sc_filename, input, "`nproc`",
+ &proj->merging_params, "crystfel.hkl") )
+ {
+ char *workdir_str = g_file_get_path(workdir);
+ job = start_slurm_job(SLURM_JOB_AMBIGATOR,
+ sc_filename, job_title, workdir_str,
+ opts->partition, opts->email_address);
+ g_free(workdir_str);
+ } else {
+ job = NULL;
+ }
+ g_free(sc_filename);
+
+ if ( job != NULL ) {
+ char **streams = malloc(sizeof(char *));
+ if ( streams != NULL ) {
+ streams[0] = stream_str;
+ add_indexing_result(proj, strdup(job_title), streams, 1);
+ }
+ }
+
+ g_object_unref(workdir);
+ return job;
}
@@ -705,74 +814,55 @@ static void *run_merging(const char *job_title,
void *opts_priv)
{
struct slurm_job *job;
- job_desc_msg_t job_desc_msg;
- submit_response_msg_t *resp;
- char **cmdline;
- char *cmdline_all;
- char *script;
- char **env;
- int n_env;
struct slurm_merging_opts *opts = opts_priv;
- GFile *workdir_gfile;
- int r;
+ GFile *workdir;
+ GFile *sc_gfile;
+ char *sc_filename;
- workdir_gfile = make_job_folder(job_title, job_notes);
- if ( workdir_gfile == NULL ) return NULL;
+ workdir = make_job_folder(job_title, job_notes);
+ if ( workdir == NULL ) return NULL;
- job = malloc(sizeof(struct slurm_job));
- if ( job == NULL ) return NULL;
+ sc_gfile = g_file_get_child(workdir, "run_merge.sh");
+ sc_filename = g_file_get_path(sc_gfile);
+ g_object_unref(sc_gfile);
+ if ( sc_filename == NULL ) return NULL;
- cmdline = merging_command_line("`nproc`",
- input,
- &proj->merging_params);
+ if ( !write_merge_script(sc_filename, input, "`nproc`",
+ &proj->merging_params, "crystfel.hkl") )
+ {
+ char *workdir_str = g_file_get_path(workdir);
+ job = start_slurm_job(SLURM_JOB_MERGING,
+ sc_filename, job_title, workdir_str,
+ opts->partition, opts->email_address);
+ g_free(workdir_str);
+ } else {
+ job = NULL;
+ }
+ g_free(sc_filename);
- cmdline_all = g_strjoinv(" ", cmdline);
+ if ( job != NULL ) {
- script = malloc(strlen(cmdline_all)+16);
- if ( script == NULL ) return 0;
+ GFile *hkl_gfile;
+ char *hkl;
+ char *hkl1;
+ char *hkl2;
- strcpy(script, "#!/bin/sh\n");
- strcat(script, cmdline_all);
- g_free(cmdline_all);
+ hkl_gfile = g_file_get_child(workdir, "crystfel.hkl");
+ hkl = g_file_get_path(hkl_gfile);
+ g_object_unref(hkl_gfile);
- env = create_env(&n_env, NULL);
+ hkl_gfile = g_file_get_child(workdir, "crystfel.hkl1");
+ hkl1 = g_file_get_path(hkl_gfile);
+ g_object_unref(hkl_gfile);
- slurm_init_job_desc_msg(&job_desc_msg);
- job_desc_msg.user_id = getuid();
- job_desc_msg.group_id = getgid();
- job_desc_msg.mail_user = safe_strdup(opts->email_address);
- job_desc_msg.mail_type = MAIL_JOB_FAIL;
- job_desc_msg.comment = "Submitted via CrystFEL GUI";
- job_desc_msg.shared = 0;
- job_desc_msg.time_limit = 60;
- job_desc_msg.partition = safe_strdup(opts->partition);
- job_desc_msg.min_nodes = 1;
- job_desc_msg.max_nodes = 1;
- job_desc_msg.name = safe_strdup(job_title);
- job_desc_msg.std_err = strdup("stderr.log");
- job_desc_msg.std_out = strdup("stdout.log");
- job_desc_msg.work_dir = g_file_get_path(workdir_gfile);
- job_desc_msg.script = script;
- job_desc_msg.environment = env;
- job_desc_msg.env_size = n_env;
+ hkl_gfile = g_file_get_child(workdir, "crystfel.hkl2");
+ hkl2 = g_file_get_path(hkl_gfile);
+ g_object_unref(hkl_gfile);
- r = slurm_submit_batch_job(&job_desc_msg, &resp);
- if ( r ) {
- ERROR("Couldn't submit job: %i\n", errno);
- return 0;
+ add_merge_result(proj, strdup(job_title), hkl, hkl1, hkl2);
}
- free(job_desc_msg.mail_user);
- free(job_desc_msg.partition);
- free(job_desc_msg.name);
- free(job_desc_msg.work_dir);
- free(job_desc_msg.std_err);
- free(job_desc_msg.std_out);
-
- job->job_id = resp->job_id;
- job->type = SLURM_JOB_MERGING;
- slurm_free_submit_response_response_msg(resp);
-
+ g_object_unref(workdir);
return job;
}
diff --git a/src/gui_merge.c b/src/gui_merge.c
index 11d48117..d561c2da 100644
--- a/src/gui_merge.c
+++ b/src/gui_merge.c
@@ -343,187 +343,6 @@ gint merge_sig(GtkWidget *widget, struct crystfelproject *proj)
}
-static GSList *append_arg_str(GSList *args,
- const char *label,
- const char *val)
-{
- size_t len;
- char *str;
-
- len = strlen(label)+strlen(val)+4;
- str = malloc(len);
- if ( str == NULL ) return args;
- snprintf(str, 63, "--%s=%s", label, val);
-
- return g_slist_append(args, str);
-}
-
-
-static GSList *append_arg_int(GSList *args,
- const char *label,
- int val)
-{
- char *str = malloc(64);
- if ( str == NULL ) return args;
- snprintf(str, 63, "--%s=%i", label, val);
- return g_slist_append(args, str);
-}
-
-
-static GSList *append_arg_float(GSList *args,
- const char *label,
- float val)
-{
- char *str = malloc(64);
- if ( str == NULL ) return args;
- snprintf(str, 63, "--%s=%f", label, val);
- return g_slist_append(args, str);
-}
-
-
-static GSList *process_hkl_command_line(struct gui_indexing_result *input,
- struct merging_params *params)
-{
- GSList *args = NULL;
- char *exe_path;
- int i;
-
- exe_path = get_crystfel_exe("process_hkl");
- if ( exe_path == NULL ) return NULL;
- args = g_slist_append(args, exe_path);
-
- for ( i=0; i<input->n_streams; i++ ) {
- args = g_slist_append(args, input->streams[i]);
- }
-
- args = g_slist_append(args, "-o");
- args = g_slist_append(args, "crystfel.hkl");
-
- args = append_arg_str(args, "symmetry", params->symmetry);
-
- if ( params->scale ) {
- args = g_slist_append(args, strdup("--scale"));
- }
-
- args = append_arg_str(args, "polarisation",
- params->polarisation);
-
- args = append_arg_int(args, "min-measurements",
- params->min_measurements);
-
- args = append_arg_float(args, "max-adu", params->max_adu);
-
- args = append_arg_float(args, "min-res", params->min_res);
-
- args = append_arg_float(args, "push-res", params->push_res);
-
- return args;
-}
-
-
-static GSList *partialator_command_line(const char *n_thread_str,
- struct gui_indexing_result *input,
- struct merging_params *params)
-{
- GSList *args = NULL;
- char *exe_path;
- int i;
-
- exe_path = get_crystfel_exe("partialator");
- if ( exe_path == NULL ) return NULL;
- args = g_slist_append(args, exe_path);
-
- for ( i=0; i<input->n_streams; i++ ) {
- args = g_slist_append(args, input->streams[i]);
- }
-
- args = g_slist_append(args, "-o");
- args = g_slist_append(args, "crystfel.hkl");
-
- args = append_arg_str(args, "symmetry", params->symmetry);
-
- args = g_slist_append(args, "-j");
- args = g_slist_append(args, strdup(n_thread_str));
-
- if ( params->twin_sym != NULL ) {
- args = g_slist_append(args, "-w");
- args = g_slist_append(args, strdup(params->twin_sym));
- }
-
- if ( params->custom_split != NULL ) {
- args = append_arg_str(args, "custom-split",
- params->custom_split);
- }
-
- if ( !params->scale ) {
- args = g_slist_append(args, "--no-scale");
- }
-
- if ( !params->bscale ) {
- args = g_slist_append(args, "--no-bscale");
- }
-
- if ( !params->postref ) {
- args = g_slist_append(args, "--no-pr");
- }
-
- if ( !params->deltacchalf ) {
- args = g_slist_append(args, "--no-deltacchalf");
- }
-
- args = append_arg_int(args, "iterations", params->niter);
-
- args = append_arg_str(args, "polarisation",
- params->polarisation);
-
- args = append_arg_int(args, "min-measurements",
- params->min_measurements);
-
- args = append_arg_float(args, "max-adu", params->max_adu);
-
- args = append_arg_float(args, "min-res", params->min_res);
-
- args = append_arg_float(args, "push-res", params->push_res);
-
- return args;
-}
-
-
-char **merging_command_line(const char *n_thread_str,
- struct gui_indexing_result *input,
- struct merging_params *params)
-{
- GSList *args;
- char **arg_strings;
- GSList *args2;
- int i, n;
-
- if ( strcmp(params->model, "process_hkl") == 0 ) {
- args = process_hkl_command_line(input, params);
- } else {
- args = partialator_command_line(n_thread_str,
- input,
- params);
- }
-
- if ( args == NULL ) return NULL;
-
- n = g_slist_length(args);
- arg_strings = malloc((n+1)*sizeof(char *));
- if ( arg_strings == NULL ) return NULL;
-
- args2 = args;
- for ( i=0; i<n; i++ ) {
- arg_strings[i] = args2->data;
- args2 = args2->next;
- }
- arg_strings[n] = NULL;
- g_slist_free(args);
-
- return arg_strings;
-}
-
-
static int write_partialator_script(const char *filename,
struct gui_indexing_result *input,
const char *n_thread_str,
@@ -537,6 +356,8 @@ static int write_partialator_script(const char *filename,
fh = fopen(filename, "w");
if ( fh == NULL ) return 1;
+ fprintf(fh, "#!/bin/sh\n");
+
exe_path = get_crystfel_exe("partialator");
if ( exe_path == NULL ) return 1;
fprintf(fh, "%s \\\n", exe_path);
diff --git a/src/gui_merge.h b/src/gui_merge.h
index 46d6dcaf..460c5fce 100644
--- a/src/gui_merge.h
+++ b/src/gui_merge.h
@@ -36,10 +36,6 @@
extern gint merge_sig(GtkWidget *widget,
struct crystfelproject *proj);
-extern char **merging_command_line(const char *n_thread_str,
- struct gui_indexing_result *input,
- struct merging_params *params);
-
extern int write_merge_script(const char *filename,
struct gui_indexing_result *input,
const char *n_thread_str,