summaryrefslogtreecommitdiff
path: root/build-aux
diff options
context:
space:
mode:
authorLuke T. Shumaker <lukeshu@lukeshu.com>2025-03-06 23:40:32 -0700
committerLuke T. Shumaker <lukeshu@lukeshu.com>2025-03-09 03:09:22 -0600
commita8398b214dd6bb27cf9f8b091f0ed6fae87eb8e4 (patch)
treeafd220fc6d1748bba338a764464092e9034a9cb7 /build-aux
parent7ae3a3769ea26b1be495f5efc3115aa2ce1b4c04 (diff)
stack.c.gen: FIX: Think harder about printf
Diffstat (limited to 'build-aux')
-rwxr-xr-xbuild-aux/stack.c.gen81
1 files changed, 58 insertions, 23 deletions
diff --git a/build-aux/stack.c.gen b/build-aux/stack.c.gen
index 1f87b54..0a77c1a 100755
--- a/build-aux/stack.c.gen
+++ b/build-aux/stack.c.gen
@@ -789,6 +789,63 @@ class LibMiscPlugin:
return False
+class PicoFmtPlugin:
+ known_out: dict[str, str]
+ known_fct: dict[str, str]
+
+ def __init__(self) -> None:
+ self.known_out = {
+ "": "_out_null", # XXX
+ "__wrap_sprintf": "_out_buffer",
+ "__wrap_snprintf": "_out_buffer",
+ "__wrap_vsnprintf": "_out_buffer",
+ "vfctprintf": "_out_fct",
+ }
+ self.known_fct = {
+ "stdio_vprintf": "stdio_buffered_printer",
+ "__wrap_vprintf": "stdio_buffered_printer",
+ }
+
+ def is_intrhandler(self, name: QName) -> bool:
+ return False
+
+ def extra_nodes(self) -> typing.Collection[Node]:
+ return []
+
+ def indirect_callees(
+ self, loc: str, line: str
+ ) -> tuple[typing.Collection[QName], bool] | None:
+ if "/3rd-party/pico-sdk/" not in loc:
+ return None
+ if "/printf.c:" in loc:
+ m = re_call_other.fullmatch(line)
+ call: str | None = m.group("func") if m else None
+ if call == "out":
+ return [QName(x) for x in self.known_out.values()], False
+ if "->fct" in line:
+ return [QName(x) for x in self.known_fct.values()], False
+ return None
+
+ def skip_call(self, chain: list[QName], call: QName) -> bool:
+ if str(call.base()) in self.known_out.values():
+ out = ""
+ for pcall in chain:
+ if str(pcall.base()) in self.known_out:
+ out = self.known_out[str(pcall.base())]
+ if (
+ out == "_out_buffer" and str(call.base()) == "_out_null"
+ ): # XXX: Gross hack
+ out = "_out_null"
+ return str(call.base()) != out
+ if str(call.base()) in self.known_fct.values():
+ fct = ""
+ for pcall in chain:
+ if str(pcall.base()) in self.known_fct:
+ fct = self.known_fct[str(pcall.base())]
+ return str(call.base()) != fct
+ return False
+
+
class PicoSDKPlugin:
app_init_array: typing.Collection[QName]
app_preinit_array: typing.Collection[QName]
@@ -862,15 +919,6 @@ class PicoSDKPlugin:
return [QName("rom_hword_as_ptr(BOOTROM_TABLE_LOOKUP_OFFSET)")], False
if "/flash.c:" in loc and "boot2_copyout" in line:
return [QName("_stage2_boot")], False
- if "/printf.c:" in loc:
- if call == "out":
- return [
- QName("_out_buffer"),
- QName("_out_null"),
- QName("_out_fct"),
- ], False
- if "->fct(" in line:
- return [QName("stdio_buffered_printer")], False
if "/stdio.c:" in loc:
if call == "out_func":
return [
@@ -894,20 +942,6 @@ class PicoSDKPlugin:
return None
def skip_call(self, chain: list[QName], call: QName) -> bool:
- if str(call.base()) in ["_out_buffer", "_out_fct"]:
- last = ""
- for pcall in chain:
- if str(pcall.base()) in [
- "__wrap_sprintf",
- "__wrap_snprintf",
- "__wrap_vsnprintf",
- "vfctprintf",
- ]:
- last = str(pcall.base())
- if last == "vfctprintf":
- return str(call.base()) != "_out_fct"
- else:
- return str(call.base()) == "_out_buffer"
return False
def extra_nodes(self) -> typing.Collection[Node]:
@@ -1247,6 +1281,7 @@ def main(
if arg_pico_platform == "rp2040":
plugins += [
+ PicoFmtPlugin(),
PicoSDKPlugin(
app_init_array=[QName("register_fini")],
),