summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rwxr-xr-xbuild-aux/stack.c.gen124
-rw-r--r--cmd/sbc_harness/config/config.h12
-rw-r--r--cmd/sbc_harness/main.c2
-rw-r--r--lib9p/tests/test_server/config/config.h2
-rw-r--r--libcr/coroutine.c8
-rw-r--r--libcr/include/libcr/coroutine.h16
-rw-r--r--libcr/tests/test_matrix/config.h2
-rw-r--r--libcr_ipc/tests/config.h2
8 files changed, 113 insertions, 55 deletions
diff --git a/build-aux/stack.c.gen b/build-aux/stack.c.gen
index af5d740..07d5cfc 100755
--- a/build-aux/stack.c.gen
+++ b/build-aux/stack.c.gen
@@ -131,6 +131,18 @@ def synthetic_node(
return n
+class AnalyzeResultGroup(typing.NamedTuple):
+ rows: dict[str, int]
+ nmax: int
+ nsum: int
+
+
+class AnalyzeResult(typing.NamedTuple):
+ groups: dict[str, AnalyzeResultGroup]
+ missing: set[str]
+ dynamic: set[str]
+
+
def analyze(
*,
ci_fnames: list[str],
@@ -140,7 +152,7 @@ def analyze(
app_indirect_callees: typing.Callable[[VCGElem], list[str]],
app_skip_call: typing.Callable[[list[str], str], bool],
cfg_max_call_depth: int,
-) -> None:
+) -> AnalyzeResult:
re_node_label = re.compile(
r"(?P<funcname>[^\n]+)\n"
+ r"(?P<location>[^\n]+:[0-9]+:[0-9]+)\n"
@@ -281,10 +293,8 @@ def analyze(
]
)
- print("/*")
-
+ groups: dict[str, AnalyzeResultGroup] = dict()
for grp_name, grp_filter in app_func_filters.items():
- # Gather the data.
nmax = 0
nsum = 0
rows: dict[str, int] = {}
@@ -295,28 +305,9 @@ def analyze(
if n > nmax:
nmax = n
nsum += cnt * n
+ groups[grp_name] = AnalyzeResultGroup(rows=rows, nmax=nmax, nsum=nsum)
- # Figure sizes.
- namelen = max([len(k) for k in rows.keys()] + [len(grp_name) + 4])
- numlen = len(str(nsum))
- sep1 = ("=" * namelen) + " " + "=" * numlen
- sep2 = ("-" * namelen) + " " + "-" * numlen
-
- # Print.
- print("= " + grp_name + " " + sep1[len(grp_name) + 3 :])
- for name, num in sorted(rows.items()):
- print(f"{name.ljust(namelen)} {str(num).rjust(numlen)}")
- print(sep2)
- print(f"{'Total'.ljust(namelen)} {str(nsum).rjust(numlen)}")
- print(f"{'Maximum'.ljust(namelen)} {str(nmax).rjust(numlen)}")
- print(sep1)
-
- for funcname in sorted(missing):
- print(f"warning: missing: {funcname}")
- for funcname in sorted(dynamic):
- print(f"warning: dynamic-stack-usage: {funcname}")
-
- print("*/")
+ return AnalyzeResult(groups=groups, missing=missing, dynamic=dynamic)
################################################################################
@@ -434,10 +425,13 @@ def main(
def sbc_is_thread(name: str) -> int:
if name.endswith("_cr") and name != "lib9p_srv_read_cr":
if "9p" in name:
+ # TODO: FIXME: Sniff these numbers from config.h
+ _CONFIG_9P_NUM_SOCKS = 3
+ CONFIG_9P_SRV_MAX_REQS = 2
if "read" in name:
- return 8
+ return _CONFIG_9P_NUM_SOCKS
elif "write" in name:
- return 16
+ return _CONFIG_9P_NUM_SOCKS * CONFIG_9P_SRV_MAX_REQS
return 1
if name == "main":
return True
@@ -463,7 +457,7 @@ def main(
# 4=just 2 levels of subdirectories
# ...
#
- # TODO: Sniff this from config.h
+ # TODO: FIXME: Sniff this from config.h
CONFIG_9P_SRV_MAX_DEPTH = 3
def sbc_skip_call(chain: list[str], call: str) -> bool:
@@ -632,14 +626,12 @@ def main(
# src/rp2040/boot_stage2/boot2_${name,,}.S for name=W25Q080,
# controlled by `#define PICO_BOOT_STAGE2_{name} 1` in
# src/boards/include/boards/pico.h
- synthetic_node("_stage2_boot", 0), # TODO
+ # synthetic_node("_stage2_boot", 0), # TODO
# https://github.com/raspberrypi/pico-bootrom-rp2040
- synthetic_node(
- "rom_func_lookup(ROM_FUNC_CONNECT_INTERNAL_FLASH)", 0
- ), # TODO
- synthetic_node("rom_func_lookup(ROM_FUNC_FLASH_EXIT_XIP)", 0), # TODO
- synthetic_node("rom_func_lookup(ROM_FUNC_FLASH_FLUSH_CACHE)", 0), # TODO
- synthetic_node("rom_hword_as_ptr(BOOTROM_TABLE_LOOKUP_OFFSET)", 0), # TODO
+ # synthetic_node("rom_func_lookup(ROM_FUNC_CONNECT_INTERNAL_FLASH)", 0), # TODO
+ # synthetic_node("rom_func_lookup(ROM_FUNC_FLASH_EXIT_XIP)", 0), # TODO
+ # synthetic_node("rom_func_lookup(ROM_FUNC_FLASH_FLUSH_CACHE)", 0), # TODO
+ # synthetic_node("rom_hword_as_ptr(BOOTROM_TABLE_LOOKUP_OFFSET)", 0), # TODO
]
# TinyUSB device #################################################
@@ -736,10 +728,10 @@ def main(
synthetic_node("realloc", 8, {"_realloc_r"}),
synthetic_node("aligned_alloc", 8, {"_memalign_r"}),
synthetic_node("reallocarray", 24, {"realloc", "__errno"}),
- synthetic_node("_free_r", 0), # TODO
- synthetic_node("_malloc_r", 0), # TODO
- synthetic_node("_realloc_r", 0), # TODO
- synthetic_node("_memalign_r", 0), # TODO
+ # synthetic_node("_free_r", 0), # TODO
+ # synthetic_node("_malloc_r", 0), # TODO
+ # synthetic_node("_realloc_r", 0), # TODO
+ # synthetic_node("_memalign_r", 0), # TODO
# execution
synthetic_node("raise", 16, {"_getpid_r"}),
synthetic_node("abort", 8, {"raise", "_exit"}),
@@ -816,7 +808,7 @@ def main(
return True
return False
- analyze(
+ result = analyze(
ci_fnames=arg_ci_fnames,
extra_nodes=all_nodes,
app_func_filters={
@@ -830,6 +822,58 @@ def main(
cfg_max_call_depth=100,
)
+ def print_group(grp_name: str) -> None:
+ grp = result.groups[grp_name]
+
+ # Figure sizes.
+ namelen = max([len(k) for k in grp.rows.keys()] + [len(grp_name) + 4])
+ numlen = len(str(grp.nsum))
+ sep1 = ("=" * namelen) + " " + "=" * numlen
+ sep2 = ("-" * namelen) + " " + "-" * numlen
+
+ # Print.
+ print("= " + grp_name + " " + sep1[len(grp_name) + 3 :])
+ for name, num in sorted(grp.rows.items()):
+ print(f"{name.ljust(namelen)} {str(num).rjust(numlen)}")
+ print(sep2)
+ print(f"{'Total'.ljust(namelen)} {str(grp.nsum).rjust(numlen)}")
+ print(f"{'Maximum'.ljust(namelen)} {str(grp.nmax).rjust(numlen)}")
+ print(sep1)
+
+ def next_power_of_2(x: int) -> int:
+ return 1 << (x.bit_length())
+
+ print("#include <stddef.h> /* for size_t */")
+ print()
+ print("/*")
+ print_group("Threads")
+ print_group("Interrupt handlers")
+ print("*/")
+ overhead = result.groups["Interrupt handlers"].nmax
+ rows: list[tuple[str, int, int]] = []
+ for funcname, base in result.groups["Threads"].rows.items():
+ rows.append((funcname.split(":")[-1], base, next_power_of_2(base + overhead)))
+ namelen = max(len(r[0]) for r in rows)
+ baselen = max(len(str(r[1])) for r in rows)
+ sizelen = max(len(str(r[2])) for r in rows)
+ for row in sorted(rows):
+ if row[0] == "main":
+ continue
+ print("const size_t CONFIG_COROUTINE_STACK_SIZE_", end="")
+ print(f"{row[0].ljust(namelen)} =", end="")
+ print(f" {str(row[2]).rjust(sizelen)};", end="")
+ print(f" /* LM_NEXT_POWER_OF_2({str(row[1]).rjust(baselen)}+{overhead}) */")
+ print()
+ print("/*")
+ print_group("Misc")
+
+ for funcname in sorted(result.missing):
+ print(f"warning: missing: {funcname}")
+ for funcname in sorted(result.dynamic):
+ print(f"warning: dynamic-stack-usage: {funcname}")
+
+ print("*/")
+
if __name__ == "__main__":
pico_platform = sys.argv[1]
diff --git a/cmd/sbc_harness/config/config.h b/cmd/sbc_harness/config/config.h
index 6046b31..b569cd5 100644
--- a/cmd/sbc_harness/config/config.h
+++ b/cmd/sbc_harness/config/config.h
@@ -7,6 +7,8 @@
#ifndef _CONFIG_H_
#define _CONFIG_H_
+#include <stddef.h> /* for size_t */
+
/* W5500 **********************************************************************/
/**
@@ -86,7 +88,13 @@
/* COROUTINE ******************************************************************/
-#define CONFIG_COROUTINE_DEFAULT_STACK_SIZE (2*1024)
+extern const size_t CONFIG_COROUTINE_STACK_SIZE_dhcp_cr;
+extern const size_t CONFIG_COROUTINE_STACK_SIZE_init_cr;
+extern const size_t CONFIG_COROUTINE_STACK_SIZE_lib9p_srv_write_cr;
+extern const size_t CONFIG_COROUTINE_STACK_SIZE_read9p_cr;
+extern const size_t CONFIG_COROUTINE_STACK_SIZE_usb_common_cr;
+extern const size_t CONFIG_COROUTINE_STACK_SIZE_usb_keyboard_cr;
+extern const size_t CONFIG_COROUTINE_STACK_SIZE_w5500_irq_cr;
#define CONFIG_COROUTINE_NAME_LEN 16
#define CONFIG_COROUTINE_MEASURE_STACK 1 /* bool */
#define CONFIG_COROUTINE_PROTECT_STACK 1 /* bool */
@@ -94,7 +102,7 @@
#define CONFIG_COROUTINE_VALGRIND 0 /* bool */
#define CONFIG_COROUTINE_GDB 1 /* bool */
-#define _CONFIG_9P_NUM_SOCKS 7
+#define _CONFIG_9P_NUM_SOCKS 3 /* FIXME: bump this back up to 8 */
#define CONFIG_COROUTINE_NUM ( \
1 /* usb_common */ + \
1 /* usb_keyboard */ + \
diff --git a/cmd/sbc_harness/main.c b/cmd/sbc_harness/main.c
index 69df077..2e83476 100644
--- a/cmd/sbc_harness/main.c
+++ b/cmd/sbc_harness/main.c
@@ -221,7 +221,7 @@ COROUTINE init_cr(void *) {
coroutine_add("usb_common", usb_common_cr, NULL);
coroutine_add("usb_keyboard", usb_keyboard_cr, &globals.keyboard_chan);
//coroutine_add("hello_world", hello_world_cr, &globals.keyboard_chan);
- coroutine_add_with_stack_size(4*1024, "dhcp", dhcp_cr, NULL);
+ coroutine_add("dhcp", dhcp_cr, NULL);
for (int i = 0; i < _CONFIG_9P_NUM_SOCKS; i++) {
char name[] = {'r', 'e', 'a', 'd', '-', hexdig[i], '\0'};
coroutine_add(name, read9p_cr, NULL);
diff --git a/lib9p/tests/test_server/config/config.h b/lib9p/tests/test_server/config/config.h
index a3660e8..201cfd0 100644
--- a/lib9p/tests/test_server/config/config.h
+++ b/lib9p/tests/test_server/config/config.h
@@ -48,7 +48,7 @@
/* COROUTINE ******************************************************************/
-#define CONFIG_COROUTINE_DEFAULT_STACK_SIZE (32*1024)
+#define CONFIG_COROUTINE_STACK_SIZE_DEFAULT (32*1024)
#define CONFIG_COROUTINE_NAME_LEN 16
#define CONFIG_COROUTINE_MEASURE_STACK 1 /* bool */
#define CONFIG_COROUTINE_PROTECT_STACK 1 /* bool */
diff --git a/libcr/coroutine.c b/libcr/coroutine.c
index 39df3d5..33e8141 100644
--- a/libcr/coroutine.c
+++ b/libcr/coroutine.c
@@ -21,9 +21,6 @@
#include "config.h"
-#ifndef CONFIG_COROUTINE_DEFAULT_STACK_SIZE
- #error config.h must define CONFIG_COROUTINE_DEFAULT_STACK_SIZE (non-negative integer)
-#endif
#ifndef CONFIG_COROUTINE_NAME_LEN
#error config.h must define CONFIG_COROUTINE_NAME_LEN (non-negative integer)
#endif
@@ -630,11 +627,6 @@ cid_t coroutine_add_with_stack_size(size_t stack_size,
return child;
}
-cid_t coroutine_add(const char *name, cr_fn_t fn, void *args) {
- return coroutine_add_with_stack_size(
- CONFIG_COROUTINE_DEFAULT_STACK_SIZE, name, fn, args);
-}
-
/* coroutine_main() ***********************************************************/
void coroutine_main(void) {
diff --git a/libcr/include/libcr/coroutine.h b/libcr/include/libcr/coroutine.h
index 756352e..2505782 100644
--- a/libcr/include/libcr/coroutine.h
+++ b/libcr/include/libcr/coroutine.h
@@ -29,8 +29,14 @@
#include <stddef.h> /* for size_t */
#include <stdbool.h> /* for bool */
+/* Configuration **************************************************************/
+
#include "config.h"
+#ifndef CONFIG_COROUTINE_MEASURE_STACK
+ #error config.h must define CONFIG_COROUTINE_MEASURE_STACK (bool)
+#endif
+
/* typedefs *******************************************************************/
/**
@@ -91,8 +97,16 @@ cid_t coroutine_add_with_stack_size(size_t stack_size, const char *name, cr_fn_t
/**
* Like coroutine_add_with_stack_size(), but uses a default stack size so
* you don't need to think about it.
+ *
+ * Either define CONFIG_COROUTINE_STACK_SIZE_DEFAULT to use for all
+ * coroutines, or CONFIG_COROUTINE_STACK_SIZE_{fn} for each COROUTINE
+ * function.
*/
-cid_t coroutine_add(const char *name, cr_fn_t fn, void *args);
+#ifdef CONFIG_COROUTINE_STACK_SIZE_DEFAULT
+#define coroutine_add(name, fn, args) coroutine_add_with_stack_size(CONFIG_COROUTINE_STACK_SIZE_DEFAULT, name, fn, args)
+#else
+#define coroutine_add(name, fn, args) coroutine_add_with_stack_size(CONFIG_COROUTINE_STACK_SIZE_##fn, name, fn, args)
+#endif
/**
* The main scheduler loop. Returns if all coroutines exit.
diff --git a/libcr/tests/test_matrix/config.h b/libcr/tests/test_matrix/config.h
index becfce0..83892df 100644
--- a/libcr/tests/test_matrix/config.h
+++ b/libcr/tests/test_matrix/config.h
@@ -7,7 +7,7 @@
#ifndef _CONFIG_H_
#define _CONFIG_H_
-#define CONFIG_COROUTINE_DEFAULT_STACK_SIZE (4*1024)
+#define CONFIG_COROUTINE_STACK_SIZE_DEFAULT (4*1024)
#define CONFIG_COROUTINE_NAME_LEN 16
#define CONFIG_COROUTINE_NUM 2
diff --git a/libcr_ipc/tests/config.h b/libcr_ipc/tests/config.h
index e06c876..2a5cbc9 100644
--- a/libcr_ipc/tests/config.h
+++ b/libcr_ipc/tests/config.h
@@ -7,7 +7,7 @@
#ifndef _CONFIG_H_
#define _CONFIG_H_
-#define CONFIG_COROUTINE_DEFAULT_STACK_SIZE (4*1024)
+#define CONFIG_COROUTINE_STACK_SIZE_DEFAULT (4*1024)
#define CONFIG_COROUTINE_NAME_LEN 16
#define CONFIG_COROUTINE_NUM 8