common = tests/grub_script_blockarg.in;
};
+ script = {
+ testcase;
+ name = grub_script_setparams;
+ common = tests/grub_script_setparams.in;
+ };
+
+script = {
+ testcase;
+ name = grub_script_return;
+ common = tests/grub_script_return.in;
+};
+
program = {
testcase;
name = example_unit_test;
static unsigned long is_continue;
static unsigned long active_loops;
static unsigned long active_breaks;
+static unsigned long function_return;
+ #define GRUB_SCRIPT_SCOPE_MALLOCED 1
+ #define GRUB_SCRIPT_SCOPE_ARGS_MALLOCED 2
+
/* Scope for grub script functions. */
struct grub_script_scope
{
return GRUB_ERR_NONE;
}
+ grub_err_t
+ grub_script_setparams (grub_command_t cmd __attribute__((unused)),
+ int argc, char **args)
+ {
+ struct grub_script_scope *new_scope;
+ struct grub_script_argv argv = { 0, 0, 0 };
+
+ if (! scope)
+ return GRUB_ERR_INVALID_COMMAND;
+
+ new_scope = grub_malloc (sizeof (*new_scope));
+ if (! new_scope)
+ return grub_errno;
+
+ if (grub_script_argv_make (&argv, argc, args))
+ {
+ grub_free (new_scope);
+ return grub_errno;
+ }
+
+ new_scope->shifts = 0;
+ new_scope->argv = argv;
+ new_scope->flags = GRUB_SCRIPT_SCOPE_MALLOCED |
+ GRUB_SCRIPT_SCOPE_ARGS_MALLOCED;
+
+ replace_scope (new_scope);
+ return GRUB_ERR_NONE;
+ }
+
+grub_err_t
+grub_script_return (grub_command_t cmd __attribute__((unused)),
+ int argc, char *argv[])
+{
+ char *p;
+ unsigned long n;
+
+ if (! scope || argc > 1)
+ return grub_error (GRUB_ERR_BAD_ARGUMENT, "not in function scope");
+
+ if (argc == 0)
+ {
+ function_return = 1;
+ return grub_strtoul (grub_env_get ("?"), NULL, 10);
+ }
+
+ n = grub_strtoul (argv[0], &p, 10);
+ if (*p != '\0')
+ return grub_error (GRUB_ERR_BAD_ARGUMENT, "bad argument");
+
+ function_return = 1;
+ return n ? grub_error (GRUB_ERR_TEST_FAILURE, "false") : GRUB_ERR_NONE;
+}
+
static int
grub_env_special (const char *name)
{
ret = grub_script_execute (func->func);
+ function_return = 0;
active_loops = loops;
- scope = old_scope;
+ replace_scope (old_scope); /* free any scopes by setparams */
return ret;
}
static grub_command_t cmd_break;
static grub_command_t cmd_continue;
static grub_command_t cmd_shift;
+ static grub_command_t cmd_setparams;
+static grub_command_t cmd_return;
void
grub_script_init (void)
N_("[n]"), N_("Continue loops"));
cmd_shift = grub_register_command ("shift", grub_script_shift,
N_("[n]"), N_("Shift positional parameters."));
+ cmd_setparams = grub_register_command ("setparams", grub_script_setparams,
+ N_("[VALUE]..."),
+ N_("Set positional parameters."));
+ cmd_return = grub_register_command ("return", grub_script_return,
+ N_("[n]"), N_("Return from a function."));
}
void
grub_unregister_command (cmd_shift);
cmd_shift = 0;
+ if (cmd_setparams)
+ grub_unregister_command (cmd_setparams);
+ cmd_setparams = 0;
++
+ if (cmd_return)
+ grub_unregister_command (cmd_return);
+ cmd_return = 0;
}
/* SHIFT command for GRUB script. */
grub_err_t grub_script_shift (grub_command_t cmd, int argc, char *argv[]);
+ /* SETPARAMS command for GRUB script functions. */
+ grub_err_t grub_script_setparams (grub_command_t cmd, int argc, char *argv[]);
+
+/* RETURN command for functions. */
+grub_err_t grub_script_return (grub_command_t cmd, int argc, char *argv[]);
+
/* This variable points to the parsed command. This is used to
communicate with the bison code. */
extern struct grub_script_cmd *grub_script_parsed;