[PATCH 1/1] cmd/setexpr: support concatenation of direct strings
Heinrich Schuchardt
heinrich.schuchardt at canonical.com
Sat Dec 21 16:14:35 CET 2024
Up to now the setexpr command only supported concatenating string provided
by reference. Allow directly passing stings.
With this patch
setexpr.s foo '1' + '3'
sets variable $foo to the value '13'.
Update the unit test for "setexpr.s fred 0".
Add a new unit test for "setexpr.s fred '1' + '3'".
Signed-off-by: Heinrich Schuchardt <heinrich.schuchardt at canonical.com>
---
cmd/setexpr.c | 54 ++++++++++++++++++++++++++++++++--------------
test/cmd/setexpr.c | 7 +++++-
2 files changed, 44 insertions(+), 17 deletions(-)
diff --git a/cmd/setexpr.c b/cmd/setexpr.c
index e111b8ba98a..c45fa85c887 100644
--- a/cmd/setexpr.c
+++ b/cmd/setexpr.c
@@ -35,9 +35,37 @@ struct expr_arg {
};
};
+/**
+ * arg_set_str() - copy string to expression argument
+ *
+ * The string is truncated to 64 KiB plus NUL terminator.
+ *
+ * @p: pointer to string
+ * @argp: pointer to expression argument
+ * Return: 0 on success, -ENOMEM if out of memory
+ */
+static int arg_set_str(void *p, struct expr_arg *argp)
+{
+ int len;
+ char *str;
+
+ /* Maximum string length of 64 KiB plus NUL terminator */
+ len = strnlen((char *)p, SZ_64K) + 1;
+ str = malloc(len);
+ if (!str) {
+ printf("Out of memory\n");
+ return -ENOMEM;
+ }
+ memcpy(str, p, len);
+ str[len - 1] = '\0';
+ argp->sval = str;
+ return 0;
+}
+
static int get_arg(char *s, int w, struct expr_arg *argp)
{
struct expr_arg arg;
+ int ret;
/*
* If the parameter starts with a '*' then assume it is a pointer to
@@ -47,8 +75,6 @@ static int get_arg(char *s, int w, struct expr_arg *argp)
ulong *p;
ulong addr;
ulong val;
- int len;
- char *str;
addr = hextoul(&s[1], NULL);
switch (w) {
@@ -66,18 +92,10 @@ static int get_arg(char *s, int w, struct expr_arg *argp)
break;
case CMD_DATA_SIZE_STR:
p = map_sysmem(addr, SZ_64K);
-
- /* Maximum string length of 64KB plus terminator */
- len = strnlen((char *)p, SZ_64K) + 1;
- str = malloc(len);
- if (!str) {
- printf("Out of memory\n");
- return -ENOMEM;
- }
- memcpy(str, p, len);
- str[len - 1] = '\0';
+ ret = arg_set_str(p, &arg);
unmap_sysmem(p);
- arg.sval = str;
+ if (ret)
+ return ret;
break;
case 4:
p = map_sysmem(addr, sizeof(u32));
@@ -93,9 +111,13 @@ static int get_arg(char *s, int w, struct expr_arg *argp)
break;
}
} else {
- if (w == CMD_DATA_SIZE_STR)
- return -EINVAL;
- arg.ival = hextoul(s, NULL);
+ if (w == CMD_DATA_SIZE_STR) {
+ ret = arg_set_str(s, &arg);
+ if (ret)
+ return ret;
+ } else {
+ arg.ival = hextoul(s, NULL);
+ }
}
*argp = arg;
diff --git a/test/cmd/setexpr.c b/test/cmd/setexpr.c
index 21a3268bd81..00d373f35ae 100644
--- a/test/cmd/setexpr.c
+++ b/test/cmd/setexpr.c
@@ -310,7 +310,8 @@ static int setexpr_test_str(struct unit_test_state *uts)
ut_assertok(env_set("fred", "x"));
start_mem = ut_check_free();
strcpy(buf, "hello");
- ut_asserteq(1, run_command("setexpr.s fred 0", 0));
+ ut_asserteq(0, run_command("setexpr.s fred 0", 0));
+ ut_asserteq_str("0", env_get("fred"));
ut_assertok(ut_check_delta(start_mem));
ut_assertok(env_set("fred", "12345"));
@@ -335,6 +336,10 @@ static int setexpr_test_str_oper(struct unit_test_state *uts)
ulong start_mem;
char *buf;
+ /* Test concatenation of strings */
+ ut_assertok(run_command("setexpr.s fred '1' + '3'", 0));
+ ut_asserteq_str("13", env_get("fred"));
+
buf = map_sysmem(0, BUF_SIZE);
memset(buf, '\xff', BUF_SIZE);
strcpy(buf, "hello");
--
2.47.1
More information about the U-Boot
mailing list