diff options
author | Michael Brown | 2012-07-20 13:36:41 +0200 |
---|---|---|
committer | Michael Brown | 2012-07-20 13:45:15 +0200 |
commit | 5d3c368efbc23d0e85e7bb3fa20c3766bfafd88a (patch) | |
tree | 3fc7bc18dc96317acbd55ba7fecc8c956507b7d8 /src/hci | |
parent | [image] Add "--autofree" option (diff) | |
download | ipxe-5d3c368efbc23d0e85e7bb3fa20c3766bfafd88a.tar.gz ipxe-5d3c368efbc23d0e85e7bb3fa20c3766bfafd88a.tar.xz ipxe-5d3c368efbc23d0e85e7bb3fa20c3766bfafd88a.zip |
[image] Add "--replace" option
Expose image tail-recursion to iPXE scripts via the "--replace"
option. This functions similarly to exec() under Unix: the
currently-executing script is replaced with the new image (as opposed
to running the new image as a subroutine).
Signed-off-by: Michael Brown <mcb30@ipxe.org>
Diffstat (limited to 'src/hci')
-rw-r--r-- | src/hci/commands/image_cmd.c | 59 |
1 files changed, 54 insertions, 5 deletions
diff --git a/src/hci/commands/image_cmd.c b/src/hci/commands/image_cmd.c index 38d814cd..0a4232f2 100644 --- a/src/hci/commands/image_cmd.c +++ b/src/hci/commands/image_cmd.c @@ -26,6 +26,7 @@ FILE_LICENCE ( GPL2_OR_LATER ); #include <ipxe/image.h> #include <ipxe/command.h> #include <ipxe/parseopt.h> +#include <ipxe/shell.h> #include <usr/imgmgmt.h> /** @file @@ -38,6 +39,8 @@ FILE_LICENCE ( GPL2_OR_LATER ); struct imgsingle_options { /** Image name */ const char *name; + /** Replace image */ + int replace; /** Free image after execution */ int autofree; }; @@ -46,6 +49,8 @@ struct imgsingle_options { static struct option_descriptor imgsingle_opts[] = { OPTION_DESC ( "name", 'n', required_argument, struct imgsingle_options, name, parse_string ), + OPTION_DESC ( "replace", 'r', no_argument, + struct imgsingle_options, replace, parse_flag ), OPTION_DESC ( "autofree", 'a', no_argument, struct imgsingle_options, autofree, parse_flag ), }; @@ -66,7 +71,8 @@ struct imgsingle_descriptor { /** Pre-action to take upon image, or NULL */ void ( * preaction ) ( struct image *image ); /** Action to take upon image, or NULL */ - int ( * action ) ( struct image *image ); + int ( * action ) ( struct image *image, + struct imgsingle_options *opts ); /** Verb to describe action */ const char *verb; }; @@ -145,7 +151,7 @@ static int imgsingle_exec ( int argc, char **argv, /* Carry out command action, if applicable */ if ( desc->action ) { - if ( ( rc = desc->action ( image ) ) != 0 ) { + if ( ( rc = desc->action ( image, &opts ) ) != 0 ) { printf ( "Could not %s: %s\n", desc->verb, strerror ( rc ) ); goto err_action; @@ -188,11 +194,23 @@ static int imgfetch_exec ( int argc, char **argv ) { return imgsingle_exec ( argc, argv, &imgfetch_desc ); } +/** + * "imgselect" command action + * + * @v image Image + * @v opts Options + * @ret rc Return status code + */ +static int imgselect ( struct image *image, + struct imgsingle_options *opts __unused ) { + return image_select ( image ); +} + /** "imgselect" family command descriptor */ struct imgsingle_descriptor imgselect_desc = { .cmd = &imgsingle_cmd, .acquire = imgacquire, - .action = image_select, + .action = imgselect, .verb = "select", }; @@ -211,13 +229,44 @@ static int imgselect_exec ( int argc, char **argv ) { static struct command_descriptor imgexec_cmd = COMMAND_DESC ( struct imgsingle_options, imgsingle_opts, 0, MAX_ARGUMENTS, - "[--autofree] [<uri|image> [<arguments>...]]" ); + "[--autofree] [--replace] " + "[<uri|image> [<arguments>...]]" ); + +/** + * "imgexec" command action + * + * @v image Image + * @v opts Options + * @ret rc Return status code + */ +static int imgexec ( struct image *image, struct imgsingle_options *opts ) { + int rc; + + /* Perform replacement or execution as applicable */ + if ( opts->replace ) { + + /* Try to replace image */ + if ( ( rc = image_replace ( image ) ) != 0 ) + return rc; + + /* Stop script and tail-recurse into replacement image */ + shell_stop ( SHELL_STOP_COMMAND_SEQUENCE ); + + } else { + + /* Try to execute image */ + if ( ( rc = image_exec ( image ) ) != 0 ) + return rc; + } + + return 0; +} /** "imgexec" family command descriptor */ struct imgsingle_descriptor imgexec_desc = { .cmd = &imgexec_cmd, .acquire = imgacquire, - .action = image_exec, + .action = imgexec, .verb = "boot", }; |