From 28a031f9b9a5a6eab0cb101d30ffbb10697b5885 Mon Sep 17 00:00:00 2001 From: Qiyuan Zhang Date: Thu, 1 Aug 2024 18:24:55 -0400 Subject: [PATCH] qualcommax: add kernel cmdline replacement hack Add kernel cmdline replacement hack to qualcommax. Now we can find and replace cmdline by setting bootargs-find-1, bootargs-replace-1, bootargs-exact-match-1 and bootargs-find-2, bootargs-replace-2, bootargs-exact-match-2 under the chosen node in the device tree. The goal of thie hack is to to add support for Linksys MX4300, a dual firmware AP. This device's default kernel command lines aren't compatiailbe with OpenWrt's UBI, so we leverage find and replace to dynamically patch the cmd from u-boot. Signed-off-by: Qiyuan Zhang --- .../arm64/boot/dts/qcom/ipq8174-mx4300.dts | 11 +++ .../0911-arm64-cmdline-replacement.patch | 87 +++++++++++++++++++ 2 files changed, 98 insertions(+) create mode 100644 target/linux/qualcommax/patches-6.6/0911-arm64-cmdline-replacement.patch diff --git a/target/linux/qualcommax/files/arch/arm64/boot/dts/qcom/ipq8174-mx4300.dts b/target/linux/qualcommax/files/arch/arm64/boot/dts/qcom/ipq8174-mx4300.dts index 6f47b6fd13682d..08c574c936c688 100644 --- a/target/linux/qualcommax/files/arch/arm64/boot/dts/qcom/ipq8174-mx4300.dts +++ b/target/linux/qualcommax/files/arch/arm64/boot/dts/qcom/ipq8174-mx4300.dts @@ -7,6 +7,17 @@ / { model = "Linksys MX4300"; compatible = "linksys,mx4300", "qcom,ipq8074"; + + chosen { + // Replace the bootargs from u-boot with find and replace + bootargs-find-1 = "init=/sbin/init rootfstype=squashfs ubi.mtd=22,2048 ubi.block=0,0 root=/dev/ubiblock0_0 rootwait ro"; + bootargs-exact-match-1 = "y"; + bootargs-replace-1 = "init=/sbin/init rootfstype=squashfs ubi.mtd=22,4096 ubi.block=0,0 root=/dev/ubiblock0_0 rootwait ro"; + + bootargs-find-2 = "init=/sbin/init rootfstype=squashfs ubi.mtd=24,2048 ubi.block=0,0 root=/dev/ubiblock0_0 rootwait ro"; + bootargs-exact-match-2 = "y"; + bootargs-replace-2 = "init=/sbin/init rootfstype=squashfs ubi.mtd=24,4096 ubi.block=0,0 root=/dev/ubiblock0_0 rootwait ro"; + }; }; &qpic_nand { diff --git a/target/linux/qualcommax/patches-6.6/0911-arm64-cmdline-replacement.patch b/target/linux/qualcommax/patches-6.6/0911-arm64-cmdline-replacement.patch new file mode 100644 index 00000000000000..d779e37ea7b213 --- /dev/null +++ b/target/linux/qualcommax/patches-6.6/0911-arm64-cmdline-replacement.patch @@ -0,0 +1,87 @@ +--- a/drivers/of/fdt.c ++++ b/drivers/of/fdt.c +@@ -1157,6 +1157,14 @@ int __init early_init_dt_scan_chosen(cha + const void *rng_seed; + const void *fdt = initial_boot_params; + ++ int i, cmd_len, f_len, r_len, offset, step; ++ char *s_ptr, *l_end, *r_end, *cur_ptr, *end_ptr; ++ const char *exact_match; ++ const int bootargs_replace_num = 2; ++ const char *bootargs_replace_props[2][3] = ++ { {"bootargs-find-1", "bootargs-replace-1", "bootargs-exact-match-1"}, ++ {"bootargs-find-2", "bootargs-replace-2", "bootargs-exact-match-2"} }; ++ + node = fdt_path_offset(fdt, "/chosen"); + if (node < 0) + node = fdt_path_offset(fdt, "/chosen@0"); +@@ -1185,6 +1193,69 @@ int __init early_init_dt_scan_chosen(cha + p = of_get_flat_dt_prop(node, "bootargs", &l); + if (p != NULL && l > 0) + strscpy(cmdline, p, min(l, COMMAND_LINE_SIZE)); ++ ++ for(i = 0; i < bootargs_replace_num; i++) { ++ p = of_get_flat_dt_prop(node, bootargs_replace_props[i][0], &f_len); ++ ++ if (p == NULL || f_len == 0 ) ++ continue; ++ ++ exact_match = of_get_flat_dt_prop(node, bootargs_replace_props[i][2], &l); ++ ++ if (exact_match != NULL && l > 0 && exact_match[0] == 'y') { ++ if(strncmp(cmdline, p, r_len) == 0) ++ s_ptr = cmdline; ++ else ++ s_ptr = NULL; ++ } else { ++ s_ptr = strstr(cmdline, p); ++ } ++ ++ if(!s_ptr) ++ continue; ++ ++ p = of_get_flat_dt_prop(node, bootargs_replace_props[i][1], &r_len); ++ ++ if (p == NULL || r_len == 0) ++ continue; ++ ++ pr_info("Input kernel commad line: %s\n", cmdline); ++ ++ cmd_len = strlen(cmdline); ++ ++ if (cmd_len - f_len + r_len < COMMAND_LINE_SIZE) { ++ ++ pr_info("Replace kernel command line with %s\n", bootargs_replace_props[i][1]); ++ ++ offset = r_len - f_len; ++ ++ if (offset != 0) { ++ l_end = s_ptr + f_len - 1; ++ r_end = cmdline + cmd_len; ++ ++ if (offset > 0) { ++ step = -1; ++ cur_ptr = r_end; ++ end_ptr = l_end + step; ++ } else { ++ step = 1; ++ cur_ptr = l_end; ++ end_ptr = r_end + step; ++ } ++ ++ for (; cur_ptr != end_ptr; cur_ptr += step) ++ *(cur_ptr + offset) = *cur_ptr; ++ } ++ ++ strncpy(s_ptr, p, r_len - 1); ++ ++ pr_info("Kernel command line after replacement: %s\n", cmdline); ++ } else { ++ pr_err("Replace kernel command line with %s failed\n", bootargs_replace_props[i][1]); ++ } ++ ++ } ++ + p = of_get_flat_dt_prop(node, "bootargs-append", &l); + if (p != NULL && l > 0) + strlcat(cmdline, p, min_t(int, strlen(cmdline) + (int)l, COMMAND_LINE_SIZE));