123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447 |
- /*****************************************************************************\
- * spank.h - Stackable Plug-in Architecture for Node job Kontrol
- *****************************************************************************
- * Copyright (C) 2002-2007 The Regents of the University of California.
- * Copyright (C) 2008-2010 Lawrence Livermore National Security.
- * Produced at Lawrence Livermore National Laboratory (cf, DISCLAIMER).
- * CODE-OCEC-09-009. All rights reserved.
- *
- * This file is part of Slurm, a resource management program.
- * For details, see <https://slurm.schedmd.com/>.
- * Please also read the included file: DISCLAIMER.
- *
- * Slurm is free software; you can redistribute it and/or modify it under
- * the terms of the GNU General Public License as published by the Free
- * Software Foundation; either version 2 of the License, or (at your option)
- * any later version.
- *
- * In addition, as a special exception, the copyright holders give permission
- * to link the code of portions of this program with the OpenSSL library under
- * certain conditions as described in each individual source file, and
- * distribute linked combinations including the two. You must obey the GNU
- * General Public License in all respects for all of the code used other than
- * OpenSSL. If you modify file(s) with this exception, you may extend this
- * exception to your version of the file(s), but you are not obligated to do
- * so. If you do not wish to do so, delete this exception statement from your
- * version. If you delete this exception statement from all source files in
- * the program, then also delete it here.
- *
- * Slurm is distributed in the hope that it will be useful, but WITHOUT ANY
- * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
- * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more
- * details.
- *
- * You should have received a copy of the GNU General Public License along
- * with Slurm; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
- \*****************************************************************************/
- #ifndef SPANK_H
- #define SPANK_H
- /* SPANK handle. Plug-in's context for running Slurm job
- */
- typedef struct spank_handle * spank_t;
- /* Prototype for all spank plugin operations
- */
- typedef int (spank_f) (spank_t spank, int ac, char *argv[]);
- /* SPANK plugin operations. SPANK plugin should have at least one of
- * these functions defined non-NULL.
- *
- * Plug-in callbacks are completed at the following points in slurmd:
- *
- * slurmd
- * `-> init()
- * |
- * `-> job_prolog()
- * |
- * | `-> slurmstepd
- * | `-> init ()
- * | -> process spank options
- * | -> init_post_opt ()
- * | + drop privileges (initgroups(), seteuid(), chdir())
- * | `-> user_init ()
- * | + for each task
- * | | + fork ()
- * | | |
- * | | + reclaim privileges
- * | | `-> task_init_privileged ()
- * | | |
- * | | + become_user ()
- * | | `-> task_init ()
- * | | |
- * | | + execve ()
- * | |
- * | + reclaim privileges
- * | + for each task
- * | | `-> task_post_fork ()
- * | |
- * | + for each task
- * | | + wait ()
- * | | `-> task_exit ()
- * | `-> exit ()
- * |
- * `---> job_epilog()
- * |
- * `-> slurmd_exit()
- *
- * In srun only the init(), init_post_opt() and local_user_init(), and exit()
- * callbacks are used.
- *
- * In sbatch/salloc only the init(), init_post_opt(), and exit() callbacks
- * are used.
- *
- * In slurmd proper, only the init(), slurmd_exit(), and
- * job_prolog/epilog callbacks are used.
- *
- */
- extern spank_f slurm_spank_init;
- extern spank_f slurm_spank_job_prolog;
- extern spank_f slurm_spank_init_post_opt;
- extern spank_f slurm_spank_local_user_init;
- extern spank_f slurm_spank_user_init;
- extern spank_f slurm_spank_task_init_privileged;
- extern spank_f slurm_spank_task_init;
- extern spank_f slurm_spank_task_post_fork;
- extern spank_f slurm_spank_task_exit;
- extern spank_f slurm_spank_job_epilog;
- extern spank_f slurm_spank_slurmd_exit;
- extern spank_f slurm_spank_exit;
- /* Items which may be obtained from the spank handle using the
- * spank_get_item () call. The expected list of variable arguments may
- * be found in the comments below.
- *
- * For example, S_JOB_NCPUS takes (uint16_t *), a pointer to uint16_t, so
- * the get item call would look like:
- *
- * uint16_t ncpus;
- * spank_err_t rc = spank_get_item (spank, S_JOB_NCPUS, &ncpus);
- *
- * while S_JOB_PID_TO_GLOBAL_ID takes (pid_t, uint32_t *), so it would
- * be called as:
- *
- * uint32_t global_id;
- * spank_err_t rc;
- * rc = spank_get_item (spank, S_JOB_PID_TO_GLOBAL_ID, pid, &global_id);
- */
- enum spank_item {
- S_JOB_UID, /* User id (uid_t *) */
- S_JOB_GID, /* Primary group id (gid_t *) */
- S_JOB_ID, /* Slurm job id (uint32_t *) */
- S_JOB_STEPID, /* Slurm job step id (uint32_t *) */
- S_JOB_NNODES, /* Total number of nodes in job (uint32_t *) */
- S_JOB_NODEID, /* Relative id of this node (uint32_t *) */
- S_JOB_LOCAL_TASK_COUNT, /* Number of local tasks (uint32_t *) */
- S_JOB_TOTAL_TASK_COUNT, /* Total number of tasks in job (uint32_t *) */
- S_JOB_NCPUS, /* Number of CPUs used by this job (uint16_t *) */
- S_JOB_ARGV, /* Command args (int *, char ***) */
- S_JOB_ENV, /* Job env array (char ***) */
- S_TASK_ID, /* Local task id (int *) */
- S_TASK_GLOBAL_ID, /* Global task id (uint32_t *) */
- S_TASK_EXIT_STATUS, /* Exit status of task if exited (int *) */
- S_TASK_PID, /* Task pid (pid_t *) */
- S_JOB_PID_TO_GLOBAL_ID, /* global task id from pid (pid_t, uint32_t *) */
- S_JOB_PID_TO_LOCAL_ID, /* local task id from pid (pid_t, uint32_t *) */
- S_JOB_LOCAL_TO_GLOBAL_ID,/* local id to global id (uint32_t, uint32_t *) */
- S_JOB_GLOBAL_TO_LOCAL_ID,/* global id to local id (uint32_t, uint32_t *) */
- S_JOB_SUPPLEMENTARY_GIDS,/* Array of suppl. gids (gid_t **, int *) */
- S_SLURM_VERSION, /* Current Slurm version (char **) */
- S_SLURM_VERSION_MAJOR, /* Slurm version major release (char **) */
- S_SLURM_VERSION_MINOR, /* Slurm version minor release (char **) */
- S_SLURM_VERSION_MICRO, /* Slurm version micro release (char **) */
- S_STEP_CPUS_PER_TASK, /* CPUs allocated per task (=1 if --overcommit
- * option is used, uint32_t *) */
- S_JOB_ALLOC_CORES, /* Job allocated cores in list format (char **) */
- S_JOB_ALLOC_MEM, /* Job allocated memory in MB (uint64_t *) */
- S_STEP_ALLOC_CORES, /* Step alloc'd cores in list format (char **) */
- S_STEP_ALLOC_MEM, /* Step alloc'd memory in MB (uint64_t *) */
- S_SLURM_RESTART_COUNT, /* Job restart count (uint32_t *) */
- S_JOB_ARRAY_ID, /* Slurm job array id (uint32_t *) or 0 */
- S_JOB_ARRAY_TASK_ID, /* Slurm job array task id (uint32_t *) */
- };
- typedef enum spank_item spank_item_t;
- /* SPANK error codes.
- */
- enum spank_err {
- ESPANK_SUCCESS = 0, /* Success. */
- ESPANK_ERROR = 1, /* Generic error. */
- ESPANK_BAD_ARG = 2, /* Bad argument. */
- ESPANK_NOT_TASK = 3, /* Not in task context. */
- ESPANK_ENV_EXISTS = 4, /* Environment variable exists && !overwrite */
- ESPANK_ENV_NOEXIST = 5, /* No such environment variable */
- ESPANK_NOSPACE = 6, /* Buffer too small. */
- ESPANK_NOT_REMOTE = 7, /* Function only may be called in remote context */
- ESPANK_NOEXIST = 8, /* Id/pid doesn't exist on this node */
- ESPANK_NOT_EXECD = 9, /* Lookup by pid requested, but no tasks running */
- ESPANK_NOT_AVAIL = 10,/* SPANK item not available from this callback */
- ESPANK_NOT_LOCAL = 11,/* Function only valid in local/alloc context */
- };
- typedef enum spank_err spank_err_t;
- /*
- * SPANK plugin context
- */
- enum spank_context {
- S_CTX_ERROR, /* Error obtaining current context */
- S_CTX_LOCAL, /* Local context (srun) */
- S_CTX_REMOTE, /* Remote context (slurmstepd) */
- S_CTX_ALLOCATOR, /* Allocator context (sbatch/salloc) */
- S_CTX_SLURMD, /* slurmd context */
- S_CTX_JOB_SCRIPT /* prolog/epilog context */
- };
- #define HAVE_S_CTX_SLURMD 1 /* slurmd context supported */
- #define HAVE_S_CTX_JOB_SCRIPT 1 /* job script (prolog/epilog) supported */
- typedef enum spank_context spank_context_t;
- /*
- * SPANK plugin options
- */
- /*
- * SPANK option callback. `val' is an integer value provided by
- * the plugin to distinguish between plugin-local options, `optarg'
- * is an argument passed by the user (if applicable), and `remote'
- * specifies whether this call is being made locally (e.g. in srun)
- * or remotely (e.g. in slurmstepd/slurmd).
- */
- typedef int (*spank_opt_cb_f) (int val, const char *optarg, int remote);
- struct spank_option {
- char * name; /* long option provided by plugin */
- char * arginfo; /* one word description of argument if required */
- char * usage; /* Usage text */
- int has_arg; /* Does option require argument? */
- int val; /* value to return using callback */
- spank_opt_cb_f cb; /* Callback function to check option value */
- };
- /*
- * Plugins may export a spank_options option table as symbol "spank_options".
- * This method only works in "local" and "remote" mode. To register options
- * in "allocator" mode (sbatch/salloc), use the preferred
- * spank_option_register function described below.
- */
- extern struct spank_option spank_options [];
- /*
- * SPANK plugin option table must end with the following entry:
- */
- #define SPANK_OPTIONS_TABLE_END { NULL, NULL, NULL, 0, 0, NULL }
- /*
- * Maximum allowed length of SPANK option name:
- */
- #define SPANK_OPTION_MAXLEN 75
- /* SPANK interface prototypes
- */
- #ifdef __cplusplus
- extern "C" {
- #endif
- /*
- * Return the string representation of a spank_err_t error code.
- */
- const char *spank_strerror (spank_err_t err);
- /*
- * Determine whether a given spank plugin symbol is supported
- * in this version of SPANK interface.
- *
- * Returns:
- * = 1 The symbol is supported
- * = 0 The symbol is not supported
- * = -1 Invalid argument
- */
- int spank_symbol_supported (const char *symbol);
- /*
- * Determine whether plugin is loaded in "remote" context
- *
- * Returns:
- * = 1 remote context, i.e. plugin is loaded in /slurmstepd.
- * = 0 not remote context
- * < 0 spank handle was not valid.
- */
- int spank_remote (spank_t spank);
- /*
- * Return the context in which the calling plugin is loaded.
- *
- * Returns the spank_context for the calling plugin, or SPANK_CTX_ERROR
- * if the current context cannot be determined.
- */
- spank_context_t spank_context (void);
- /*
- * Register a plugin-provided option dynamically. This function
- * is only valid when called from slurm_spank_init(), and must
- * be guaranteed to be called in all contexts in which it is
- * used (local, remote, allocator).
- *
- * This function is the only method to register options in
- * allocator context.
- *
- * May be called multiple times to register many options.
- *
- * Returns ESPANK_SUCCESS on successful registration of the option
- * or ESPANK_BAD_ARG if not called from slurm_spank_init().
- */
- spank_err_t spank_option_register (spank_t spank, struct spank_option *opt);
- /*
- * Check whether spank plugin option [opt] has been activated.
- * If the option takes an argument, then the option argument
- * (if found) will be returned in *optarg.
- * This function can be invoked from the following functions:
- * slurm_spank_job_prolog, slurm_spank_local_user_init, slurm_spank_user_init,
- * slurm_spank_task_init_privileged, slurm_spank_task_init,
- * slurm_spank_task_exit, and slurm_spank_job_epilog.
- *
- * Returns
- * ESPANK_SUCCESS if the option was used by user. In this case
- * *optarg will contain the option argument if opt->has_arg != 0.
- * ESPANK_ERROR if the option wasn't used.
- * ESPANK_BAD_ARG if an invalid argument was passed to the function,
- * such as NULL opt, NULL opt->name, or NULL optarg when opt->has_arg != 0.
- * ESPANK_NOT_AVAIL if called from improper context.
- */
- spank_err_t spank_option_getopt (spank_t spank, struct spank_option *opt,
- char **optarg);
- /* Get the value for the current job or task item specified,
- * storing the result in the subsequent pointer argument(s).
- * Refer to the spank_item_t comments for argument types.
- * For S_JOB_ARGV, S_JOB_ENV, and S_SLURM_VERSION* items
- * the result returned to the caller should not be freed or
- * modified.
- *
- * Returns ESPANK_SUCCESS on success, ESPANK_NOTASK if an S_TASK*
- * item is requested from outside a task context, ESPANK_BAD_ARG
- * if invalid args are passed to spank_get_item or spank_get_item
- * is called from an invalid context, and ESPANK_NOT_REMOTE
- * if not called from slurmstepd context or spank_local_user_init.
- */
- spank_err_t spank_get_item (spank_t spank, spank_item_t item, ...);
- /* Place a copy of environment variable "var" from the job's environment
- * into buffer "buf" of size "len."
- *
- * Returns ESPANK_SUCCESS on success, o/w spank_err_t on failure:
- * ESPANK_BAD_ARG = spank handle invalid or len < 0.
- * ESPANK_ENV_NOEXIST = environment variable doesn't exist in job's env.
- * ESPANK_NOSPACE = buffer too small, truncation occurred.
- * ESPANK_NOT_REMOTE = not called in remote context (i.e. from slurmd).
- */
- spank_err_t spank_getenv (spank_t spank, const char *var, char *buf, int len);
- /*
- * Set the environment variable "var" to "val" in the environment of
- * the current job or task in the spank handle. If overwrite != 0 an
- * existing value for var will be overwritten.
- *
- * Returns ESPANK_SUCCESS on success, o/w spank_err_t on failure:
- * ESPANK_ENV_EXISTS = var exists in job env and overwrite == 0.
- * ESPANK_BAD_ARG = spank handle invalid or var/val are NULL.
- * ESPANK_NOT_REMOTE = not called from slurmstepd.
- */
- spank_err_t spank_setenv (spank_t spank, const char *var, const char *val,
- int overwrite);
- /*
- * Unset environment variable "var" in the environment of current job or
- * task in the spank handle.
- *
- * Returns ESPANK_SUCCESS on success, o/w spank_err_t on failure:
- * ESPANK_BAD_ARG = spank handle invalid or var is NULL.
- * ESPANK_NOT_REMOTE = not called from slurmstepd.
- */
- spank_err_t spank_unsetenv (spank_t spank, const char *var);
- /*
- * Set an environment variable "name" to "value" in the "job control"
- * environment, which is an extra set of environment variables
- * included in the environment of the Slurm prolog and epilog
- * programs. Environment variables set via this function will
- * be prepended with SPANK_ to differentiate them from other env
- * vars, and to avoid security issues.
- *
- * Returns ESPANK_SUCCESS on success, o/w/ spank_err_t on failure:
- * ESPANK_ENV_EXISTS = var exists in control env and overwrite == 0.
- * ESPANK_NOT_LOCAL = not called in local context
- */
- spank_err_t spank_job_control_setenv (spank_t sp, const char *name,
- const char *value, int overwrite);
- /*
- * Place a copy of environment variable "name" from the job control
- * environment into a buffer buf of size len.
- *
- * Returns ESPANK_SUCCESS on success, o/w spank_err_t on failure:
- * ESPANK_BAD_ARG = invalid spank handle or len <= 0
- * ESPANK_ENV_NOEXIST = environment var does not exist in control env
- * ESPANK_NOSPACE = buffer too small, truncation occurred.
- * ESPANK_NOT_LOCAL = not called in local context
- */
- spank_err_t spank_job_control_getenv (spank_t sp, const char *name,
- char *buf, int len);
- /*
- * Unset environment variable "name" in the job control environment.
- *
- * Returns ESPANK_SUCCESS on success, o/w spank_err_t on failure:
- * ESPANK_BAD_ARG = invalid spank handle or var is NULL
- * ESPANK_NOT_LOCAL = not called in local context
- */
- spank_err_t spank_job_control_unsetenv (spank_t sp, const char *name);
- /*
- * Slurm logging functions which are exported to plugins.
- */
- extern void slurm_info (const char *format, ...)
- __attribute__ ((format (printf, 1, 2)));
- extern void slurm_error (const char *format, ...)
- __attribute__ ((format (printf, 1, 2)));
- extern void slurm_verbose (const char *format, ...)
- __attribute__ ((format (printf, 1, 2)));
- extern void slurm_debug (const char *format, ...)
- __attribute__ ((format (printf, 1, 2)));
- extern void slurm_debug2 (const char *format, ...)
- __attribute__ ((format (printf, 1, 2)));
- extern void slurm_debug3 (const char *format, ...)
- __attribute__ ((format (printf, 1, 2)));
- /*
- * Print at the same log level as error(), but without prefixing the message
- * with "error: ". Useful to report back to srun commands from SPANK plugins,
- * as info() will only go to the logs.
- */
- extern void slurm_spank_log(const char *, ...)
- __attribute__ ((format (printf, 1, 2)));
- #ifdef __cplusplus
- }
- #endif
- /*
- * All spank plugins must issue the following for the Slurm plugin
- * loader.
- */
- #define SPANK_PLUGIN(__name, __ver) \
- const char plugin_name [] = #__name; \
- const char plugin_type [] = "spank"; \
- const unsigned int plugin_version = __ver;
- #endif /* !SPANK_H */
|