Skip to content

fix(libc): retain short wide scanf character fields - #9863

Merged
oneandonlydean merged 16 commits into
boykopovar:mainfrom
UnhealthyKraken:fix/libc-wide-scan-short-field
Nov 4, 2026
Merged

oneandonlydean merged 16 commits into
boykopovar:mainfrom
UnhealthyKraken:fix/libc-wide-scan-short-field

Conversation

@UnhealthyKraken

@UnhealthyKraken UnhealthyKraken commented Oct 22, 2026 •

Copy link
Copy Markdown
Contributor

What

Keep a nonempty character field when wide scanf reaches EOF before its requested width. Input a with %3lc returns one assignment, stores only a without a terminator, and continues to %n or a following directive. Suppression consumes the prefix without adding an assignment; an empty field remains an input failure. Positive-capacity secure wide destinations consume at most min(width, capacity). For positive-length input, a zero-capacity wide destination adds no assignment, leaves output/errno unchanged and stops before the following %n.

Short-field behavior follows pinned FreeBSD11.4 convert_char/convert_wchar, supplemented by hypermoist's report and JJenkx's native calls to three bundled libraries. These are attributed contributor measurements, not my console measurements or firmware-wide proof. Zero-capacity consumption/empty-input precedence, narrow byte-capacity rules and native stream parity remain unverified in debt. The reported undersized narrow ASCII case remains a known gap; no test pins its unsupported exception behavior.

The review refresh retains main's public declarations, UTF-8 and %S/%C matching-failure behavior and one combined scanner debt bullet. Blazing Cook's positive-capacity contribution retains its author identity/history. The agreed order remains #9863 before #9087; names, NIDs and implemented ABI do not change.

Tested

Review revision 5f290cecde56468bb507d4c72b9de50c03eeab87, based on main 47f9cee2cd77 by history-preserving merge.

Hosted Linux actual project configure/focused build passed with matching source-built libraries: both scanner suites pass once plus five repetitions each. Conventions (0 errors; existing combined debt-length warning), whitespace, public-header audit and standalone libc/kernel header compilation pass. Linux job. Windows final-head actual project configure/affected-target build passed on hosted WinLibs GCC 15.2 Release with matching runtime libraries: 2/2 focused tests, followed by two repetitions each. Windows job. Git-only mergeability against later fetched main 504ea3b53b23 is clean; that later combined tree was not built.

Original Windows baseline/candidate and later independent contributor results remain recorded in the earlier review report and zero-capacity correction; those are historical heads, not additional final-head platform runs.

No local builds/runtime tests, games, proprietary modules or physical-console execution were performed for this revision. The full repository suite was not run.

Checklist

  • Based on current main; no other open PR implements the same functions
  • One topic per PR; follow-ups go in a new PR
  • No comments in code except technical debt
  • Unimplemented paths throw (NotImplemented_nid_no_patch); silent stubs are listed under Silent stubs in their library's technical debt file
  • No notes, investigation .md files or images added to the repository (attach them to this PR)
  • New third-party code is a submodule built from source
  • Generic behaviour, not specific to one title
  • Depends on: none
  • Fixes: none
  • Unblocks: none
  • GPUs tested: n/a
  • AI-assisted: yes

@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

@orezraey: the required overlap report identifies one documentation-line conflict with #9087. Your narrow snprintf_s/sscanf_s runtime implementation is independent of this shared wide scanner correction; I did not copy or replace it. Proposed order is #9863 first, then preserve the short-field evidence/unsupported-capacity wording together with your updated constraint wording when resolving the combined scanner debt entry. If #9087 lands first, I can apply the converse resolution. Please confirm your preferred order; I am leaving the agreement explicitly pending rather than claiming the overlap is resolved.

The base-conflicted #8306 dispatch change for %S/%C is also separate from the character-field loop. If #6044's test-directory reorganization lands first, retain these cases at its final GuestWideConversion/GuestWideStreamScan paths and registrations. No foreign branches were combined for the reported runtime tests.

@orezraey

Copy link
Copy Markdown
Contributor

@UnhealthyKraken Agreed: #9863 lands first. I'll then merge it into #9087 and resolve the combined scanner debt entry, keeping your short-field evidence and unsupported-capacity wording together with my constraint wording.

@github-actions

github-actions Bot commented Oct 22, 2026 •

Copy link
Copy Markdown

Other open pull requests touch the same code. Merging one will break the other, or both implement the same thing. If this one builds on them, list them in Depends on.

Pull request Conflicting files (lines on main) Same exports Same new files
PR 9087 docs/dev/debt/libc.md L244

Some comparisons could not be completed because a pull request conflicts with the base branch. Review these shared files manually before concluding that there is no overlap.

Pull request Shared files not compared
PR 5021 docs/dev/debt/libc.md
PR 5303 docs/dev/debt/libc.md
PR 6819 docs/dev/debt/libc.md
PR 7081 docs/dev/debt/libc.md
PR 7386 docs/dev/debt/libc.md
PR 7447 docs/dev/debt/libc.md
PR 7715 docs/dev/debt/libc.md
PR 8150 docs/dev/debt/libc.md
PR 8965 docs/dev/debt/libc.md
PR 9340 docs/dev/debt/libc.md
PR 9371 docs/dev/debt/libc.md
PR 9447 docs/dev/debt/libc.md
PR 9526 docs/dev/debt/libc.md
PR 9929 docs/dev/debt/libc.md
PR 10113 docs/dev/debt/libc.md
PR 10226 docs/dev/debt/libc.md
PR 10245 docs/dev/debt/libc.md
PR 10250 docs/dev/debt/libc.md
PR 10253 docs/dev/debt/libc.md
PR 10265 docs/dev/debt/libc.md
PR 10274 docs/dev/debt/libc.md
PR 10325 docs/dev/debt/libc.md
PR 10328 docs/dev/debt/libc.md
PR 10345 docs/dev/debt/libc.md
PR 10349 docs/dev/debt/libc.md
PR 10405 docs/dev/debt/libc.md
PR 10506 docs/dev/debt/libc.md
PR 10510 docs/dev/debt/libc.md
PR 10512 docs/dev/debt/libc.md
PR 10565 docs/dev/debt/libc.md
PR 10987 docs/dev/debt/libc.md
PR 11260 docs/dev/debt/libc.md
PR 11262 docs/dev/debt/libc.md
PR 11266 docs/dev/debt/libc.md
PR 11332 docs/dev/debt/libc.md
PR 11632 docs/dev/debt/libc.md
PR 11634 docs/dev/debt/libc.md
PR 11724 core/libs/tests/GuestWideStreamScan.cpp
docs/dev/debt/libc.md
PR 11726 core/libs/tests/GuestWideStreamScan.cpp
docs/dev/debt/libc.md
PR 11831 docs/dev/debt/libc.md
PR 11907 docs/dev/debt/libc.md
PR 12122 docs/dev/debt/libc.md
PR 12397 docs/dev/debt/libc.md
PR 12560 docs/dev/debt/libc.md
PR 12574 docs/dev/debt/libc.md
PR 12593 docs/dev/debt/libc.md
PR 12622 docs/dev/debt/libc.md
PR 12627 docs/dev/debt/libc.md
PR 12682 docs/dev/debt/libc.md
PR 12688 docs/dev/debt/libc.md
PR 12700 docs/dev/debt/libc.md
PR 12965 docs/dev/debt/libc.md
PR 13119 docs/dev/debt/libc.md
PR 13390 docs/dev/debt/libc.md
PR 13804 docs/dev/debt/libc.md
PR 14212 docs/dev/debt/libc.md
PR 14585 docs/dev/debt/libc.md
PR 14610 docs/dev/debt/libc.md

@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

Confirmed, thank you. I have updated the PR description with the agreed order and linked your confirmation: #9863 first, then #9087 merges it and preserves both sets of debt wording. This PR remains independent with Depends on: none. The current head is mergeable and hosted checks are now clean; the full product jobs remain skipped, with the focused Windows results recorded separately.

@MarcZX10 MarcZX10 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I reviewed the implementation path and the added regressions against the contributor-reported bundled-library table in #9321. The code now assigns the consumed nonempty %c/%lc prefix without a terminator, continues to later directives and %n, and leaves suppressed fields unassigned. Tests cover both string and stream scanners, secure/unsecure entry points, prior assignments, exact canary bounds, lookahead and an explicitly unsupported undersized secure-capacity case. The debt text keeps the evidence attribution and remaining limits clear. The coordinated order with #9087 is documented by both authors, and Depends on: none is consistent with the confirmed independent order.

The author reports Windows focused builds/runs and 8/8 candidate suites (9/9 including loader) against identical executables, plus 1177 test registrations. Hosted conventions, relinker and registration checks pass; hosted Linux/Windows product jobs are skipped. I did not independently run the Windows binaries here.

One freshness item: current upstream main is a0900b9d; GitHub compare reports head 26db0f2a is two commits ahead and 26 behind, with merge base d6e7ab42. CONTRIBUTING asks branches to stay current. Please rebase, preserve the agreed #9087 wording/order, and rerun the two focused scanner suites plus conventions on the final combined head before merge. No blocking behavior defect found in the reviewed diff.

@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

@MarcZX10 Refreshed onto main 3bbd232 in 36496b7 using a history-preserving merge rather than a force-pushed rebase.

Rebuilt libc and both requested test executables. guest_wide_conversion and guest_wide_stream_scan pass (2/2) on the combined head. Current conventions report zero errors and the same pre-existing combined debt-entry length warning; whitespace and test registration pass (1177 executables, none unregistered).

The four focused files are byte-for-byte unchanged from reviewed head 26db0f2. The PR description records this fresh validation separately from the original full-library/baseline comparison. The agreement with @orezraey is preserved: #9863 first, then #9087 keeps both debt wordings; Depends on remains none. No new Linux/macOS/console or full-repository run is claimed.

@MarcZX10

Copy link
Copy Markdown
Contributor

The agreed #9863-before-#9087 order is now documented, and the author reports the focused guest_wide_conversion / guest_wide_stream_scan tests pass on refreshed head 36496b70 with conventions and registration checks clean. Upstream main has since advanced to 7c900bbc; this head is 14 commits behind the tested base 3bbd2321. Please refresh and rerun the two focused suites and conventions on the final combined head. Hosted Linux/Windows product jobs are skipped; the exhaustive console-library evidence is contributor-reported.

@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

@MarcZX10 Refreshed again: fetched main was already at 44ce348, beyond the 7c900bb snapshot in your comment. Merged that snapshot without rewriting published history; new head a97e5e4.

The four focused files are byte-for-byte unchanged from 36496b7. Reconfigured and checked the libc and both scanner test build targets (Ninja: no work required), then reran guest_wide_conversion and guest_wide_stream_scan on this combined head: 2/2 pass. Conventions: zero errors, the same pre-existing 2980-character combined debt-entry warning. Whitespace and registration pass (1177 executables, none built and unregistered). CMake's unrelated object-path-length warnings remain.

The PR description records this exact tested snapshot. The #9863-before-#9087 agreement and both debt wordings are preserved. No Linux/macOS/console or full-suite runtime run is claimed; hosted product-job status remains separate from these local tests.

@Dom3005

Dom3005 commented Oct 22, 2026

Copy link
Copy Markdown
Contributor

Linux run (the description lists Linux as not tested). Docker on Windows: Ubuntu 26.04, GCC 15, glibc 2.43, WSL2 kernel 6.6, Release, BUILD_TESTING=ON. Head a97e5e4 merged onto main fcd4558 (clean).

  • guest_wide_conversion and guest_wide_stream_scan pass 5 of 5 (--repeat until-fail:5).
  • Baseline: with this PR's test kept and main's versions of the changed sources, the test fails on Linux too, so it covers the change against glibc as well as UCRT.

No findings.

AI-assisted: yes

@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

Thanks for the independent run and the Linux baseline comparison. I linked your exact-head/environment report under Tested and attributed it to you; I have not rerun Linux here. No additional code change is indicated by that report.

@MarcZX10

Copy link
Copy Markdown
Contributor

The current head a97e5e47f8083ab3a4a0a8da883c9ea51bd16e53 has strong independent evidence: the author reports the two focused scanner suites and conventions/registration checks on that head, and Dom3005 reports Linux --repeat until-fail:5 plus a main-source negative control on the same head. I compared current main against the test base 44ce348a: the intervening commits do not touch ScanningWide.cpp or either scanner test, but they do touch docs/dev/debt/libc.md. The PR is now 361 commits behind current main. Please rebase/merge current main to keep the branch current, preserve the agreed #9863-before-#9087 debt wording/order, and rerun the two focused suites plus conventions on the final head. I’m not asking to repeat the unchanged platform comparison.

@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

@MarcZX10 Merged current main 9a030c2d504965cc646091030eaade1fd4a8b8d0 into signed head c677508e0eda25afd3fd4e92f8d47b50b51a58af, preserving published history.

ScanningWide.cpp, GuestWideConversion.cpp and GuestWideStreamScan.cpp remain byte-for-byte identical to a97e5e47f. The two debt paragraphs mentioning ScanningWide.cpp are also byte-for-byte preserved through the clean merge, including the short-field evidence and unsupported-capacity wording. The agreed #9863-before-#9087 order remains unchanged.

The focused cloud validation checks out exact c677508e, runs current conventions/whitespace against the merged base, builds only the two requested test targets plus their required dependencies with one build job, then runs the two suites serially. Results are pending. No local builds were started, and this is a focused refresh rather than another platform-comparison claim.

@JJenkx

JJenkx commented Oct 23, 2026

Copy link
Copy Markdown
Contributor

Console data for the case the description leaves open: a short secure field whose destination capacity is below the requested width. This is evidence only; I haven't touched the branch.

Method. I called swscanf_s and swscanf directly in the libc.prx that three titles ship: PPSA13934, PPSA07923 and PPSA05916, decrypted modules with sha256 F0F83624…, 40061431… and 5293254B…. Each case ran natively on Windows in its own process, and __error was redirected to observe errno. The destinations were pre-filled with #.

Results. All three titles give identical results:

Call Return Destination %n errno
swscanf(L"a", L"%3lc%n", w, &n) 1 a, then untouched 1 0
swscanf_s(L"a", L"%3lc%n", w, 3, &n) 1 a 1 0
swscanf_s(L"a", L"%3lc%n", w, 2, &n) 1 a 1 0
swscanf_s(L"a", L"%3lc%n", w, 1, &n) 1 a 1 0
swscanf_s(L"a", L"%3lc%n", w, 0, &n) 0 untouched not reached 0
swscanf_s(L"ab", L"%3lc%n", w, 2, &n) 1 a b 2 0
swscanf_s(L"abc", L"%3lc%n", w, 2, &n) 1 a b 2 0
swscanf_s(L"a", L"%3c%n", c, 2 or 3, &n) 1 a (narrow) 1 0

What the console does:

  • A capacity below the requested width does not fail. The field reads at most min(width, capacity) characters.
  • With input abc, width 3 and capacity 2, it stores and consumes exactly two characters, so %n is 2. Nothing is written past the capacity, errno is not set, and no constraint handler runs. A handler call would have hit an unresolved import in this harness.
  • Only capacity 0 fails: it returns 0 before any assignment.
  • The short %3lc case without _s (return 1, a stored without a terminator) matches what this PR implements.

So the behaviour where this PR "throws after consuming the prefix" for a capacity below the requested width differs from the console. I didn't check whether a capacity-0 field consumes its input; %n is never reached there.

@oneandonlydean oneandonlydean self-assigned this Oct 23, 2026
@oneandonlydean

Copy link
Copy Markdown
Collaborator

@UnhealthyKraken The new evidence in issuecomment-6357861510 contradicts the throw at ScanningWide.cpp:431-432 and the capacity 1/2 throw assertions. The contributor reports native calls into three bundled libraries: input a, width 3 and capacity 1 or 2 succeeds with one character and %n=1; input abc and capacity 2 stores and consumes two characters, with %n=2. Capacity 0 returns zero without writing; its consumption remains unverified. Please reconcile the secure character path with that evidence, including capacity-limited consumption, update the regression assertions and debt wording, and rerun both scanner suites. Keep the evidence attribution: these are contributor-reported native library calls, not firmware-wide console proof.

@cookie42073-cmd

Copy link
Copy Markdown
Contributor

Hey @UnhealthyKraken, I put together a small follow-up for JJenkx's positive-capacity measurements above, covering the wide-destination part of the new review request. With abc, %3lc and capacity 2, it stores ab, reports %n == 2 and leaves c for the next conversion, without adding a terminator.

The attached patch limits consumption before reading, only for a nonnull, positive-capacity wide destination (%lc). A UTF-8 conversion update landed while I was checking it, so I kept narrow %c out of this correction. Its undersized-capacity case, including the reported ASCII example, remains open; the general byte-capacity behavior needs separate evidence. Short zero-capacity fields retain your explicit unsupported path because their input-consumption order is still unknown. Suppression and unsized calls keep their original width.

Tested Windows 11 Pro x64 26300, WinLibs GCC 15.2.0 r7, Release with BUILD_TESTING=ON. I merged exact c677508e0eda25afd3fd4e92f8d47b50b51a58af into main 0a0ed7216784cc5cdbadc450985d179d50ef2d03 locally (9a12b85de12fcb4bf4c01ddfff945e9317df091e), then tested follow-up commit 41ff8b1d125cfcb7c53cf846c33ccbfb71d070df.

  • Original proposed code: full build and original 10-test selection pass; adding the new regressions makes both scanner suites fail.
  • Follow-up: full build and 10/10 pass, with five additional fresh-process passes for each scanner suite.
  • Keeping the exact same two test executables and replacing only unpatched libc.prx with the frozen original library makes both failures return. Restoring the fixed library gives 10/10 again.
  • The exact final committed source also passes the full build and 10/10 with a clean checkout. The selection includes the newly merged UTF-8 locale and wcsrtombs suites. No selected test skipped.

Tests check output canaries, no terminator, %n, the following character, prior assignments, suppression argument handling, and direct/va-list stream wrappers. The format-patch applies cleanly to both your original head and the tested main integration. Conventions report zero errors and the combined scanner debt-entry length warning (3369 characters); whitespace passes.

The native bundled-library measurements are JJenkx's; this follow-up preserves your original implementation and history. These are our own Windows regression results; shared stream coverage does not establish bundled-library stream parity. Linux, macOS, full CTest, title execution and physical PS5 behavior were not tested. The agreed #9863-before-#9087 order is unchanged. No competing PR or source push; this is a patch handoff on your existing work. AI-assisted, independently reviewed before posting.

AnyPS5-9863-wide-capacity-patch-and-tests-20261023.zip

ZIP SHA-256: 84a84689382d6d4e03dd045d9b3c1b2c433a39e0c3a36e0cd5de59a98e3d1ad8.

@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

@oneandonlydean @JJenkx @cookie42073-cmd Published the positive-capacity wide-destination correction at 12446569274e168eb8e14d2bc86205b7e2d02492, after merging main 938812df1403. Blazing Cook's supplied tests and correction retain their author identity in commits c3eb4c2 and 1244656; no history rewrite.

Secure %lc now bounds consumption by positive capacity before reading, so abc / %3lc / capacity2 stores ab, leaves c, reports %n=2, and adds no terminator. The regressions cover capacities1–4, empty/short/full input, canaries, errno, preceding assignments, suppression and direct/va-list stream wrappers.

Own cloud Linux validation (Ubuntu24.04/GCC13.3, actual bundled project, one build job, serial tests): regressions before correction fail both scanner suites. Final-head candidate/control passes10/10 focused suites; restoring only the old scanner and rebuilding libc gives2fail/8pass with SHA256-verified unchanged scanner executables; restoring the correction gives10/10 again. Both scanner suites also pass five repetitions. Conventions0errors, existing3369-character debt warning; whitespace passes. No local builds/runtime tests. The supplied Windows results remain attributed to their contributor and integration, not claimed as my final-head Windows run.

The description/debt now distinguish JJenkx's reported native calls to three bundled libraries from firmware-wide or physical-console proof. This correction intentionally covers positive wide destinations. The reported narrow ASCII undersized case still differs; generalized narrow byte-capacity rules need evidence alongside main's UTF-8 changes. Short zero-capacity fields also remain explicitly unsupported: the reported return/output are known, but consumption is not. Shared stream regression coverage does not establish native bundled-library stream parity.

@JJenkx If additional measurements are available, the remaining questions are narrow %c byte limits with multibyte input and the next unread character after a zero-capacity %lc/%c stream call. I have not inferred those results or marked the full secure-capacity request resolved. The agreed #9863-before-#9087 order remains unchanged. AI-assisted: yes.

@MarcZX10 MarcZX10 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I reviewed exact head 12446569274e168eb8e14d2bc86205b7e2d02492.

One measured secure-field case is still represented as an exception, although the linked native-library results report a return value:

  • ScanningWide.cpp:432-433 throws when %3lc has a positive-length short input and capacity zero. GuestWideConversion.cpp:259-264 codifies that as an expected throw.
  • JJenkx's attributed report in the linked native calls says that, for three bundled libc.prx builds, swscanf_s(L"a", L"%3lc%n", w, 0, &n) returns 0, leaves the destination untouched, leaves errno at zero, and does not reach %n. The report explicitly leaves input consumption unknown.

Please make the zero-capacity short-field return and destination behavior match that evidence, and add a regression that checks those observed results without asserting stream/input consumption. Keep consumption marked unverified until measured. The current explicit throw is a known behavior mismatch, even though the cursor position is unknown.

The exact-head report records strong Linux validation (10/10 focused suites, including five repeat runs); I did not rerun those tests locally. Current hosted Linux and Windows product jobs are skipped, while conventions, eligibility, registration, relinker matrix and other applicable checks pass. The PR is also 8 commits behind current main (e94545a5, merge base 938812df); the merge is clean, and those intervening main commits do not touch the four changed files. Please refresh to current main and rerun both focused scanner suites and conventions before merge, as required by the contribution rules.

@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

@oneandonlydean Reconciled the two main conflicts and retained main's public-header declarations. Removed the undersized narrow %3c expected-throw/unchanged-output assertions and the stream fixture's local __error_nid_postfix declaration. Suppressed-field coverage stays. The single combined scanner debt bullet retains main's %S/%C matching-failure and UTF-8 wording alongside the short-field evidence limits. The #9863-before-#9087 order and existing authorship remain intact.

Published 5f290cecde56468bb507d4c72b9de50c03eeab87 after a history-preserving merge of main 47f9cee2cd77. Hosted Linux actual project configure/focused build passed with matching source-built libraries: both scanner suites pass once plus five repetitions each. Conventions (0 errors; existing combined debt-length warning), whitespace, public-header audit and standalone libc/kernel header compilation pass. Linux job. Windows final-head actual project configure/affected-target build passed on hosted WinLibs GCC 15.2 Release with matching runtime libraries: 2/2 focused tests, followed by two repetitions each. Windows job. Git-only mergeability against later fetched main 504ea3b53b23 is clean; that later combined tree was not built.

Updated the PR description using the current template. AI-assisted: yes. No local builds/runtime tests, games, proprietary modules or console execution; the full repository suite was not run.

@github-actions github-actions Bot removed the needs rebase Conflicts with main, rebase needed label Oct 26, 2026
@oneandonlydean

Copy link
Copy Markdown
Collaborator

@UnhealthyKraken the test and declaration changes answer those parts of my ask. The merged scanner debt bullet still says “A short %c field is currently a matching failure without storing its available prefix”, then says short %c assignments follow FreeBSD. I need the obsolete sentence beginning “A short %c field is currently” removed, including its old unverified-return/prefix clause. Keep the current short-field measurement limits, zero-capacity caveats, and main’s %S/%C and C-locale wcrtomb wording. The implementation and retained short-field tests already preserve the available prefix.

@github-actions github-actions Bot added the needs rebase Conflicts with main, rebase needed label Oct 26, 2026
@Danigamer05 Danigamer05 mentioned this pull request Oct 27, 2026
12 tasks done
@UnhealthyKraken

Copy link
Copy Markdown
Contributor Author

Merged current upstream main abed03546804 with a normal merge in b48707c24970; no force push. The conflict was confined to docs/dev/debt/libc.md. Retained upstream floating-scan errno behavior, its new regression assertions and its debt entry, together with this PR's short-field behavior and evidence limits. Removed the stale debt sentence claiming short fields still fail without writing.

Validation: actual focused Release targets built in hosted Linux and Windows; both wide conversion/stream scanner suites passed on both, including repetitions. Conventions, whitespace and public-header checks pass (the scanner PR retains its existing debt-length warning). No selected cases were skipped. Latest upstream CI has no failing or pending applicable checks, and GitHub reports the PR mergeable. No local builds or native tests were run.

@JJenkx

JJenkx commented Oct 28, 2026

Copy link
Copy Markdown
Contributor

@UnhealthyKraken a merge-order note from #12420 (swscanf: scanset ranges, string lengths and unknown conversions, measured on titles' libc.prx). The overlap check pairs it with this PR on the long swscanf entry in docs/dev/debt/libc.md (line 201). #12420 changes only that entry's "It throws for unknown length modifiers, scanset ranges, ..." sentence, so it's a text overlap, not a code one.

I'd suggest this PR land first. I'll rebase #12420 after it, so you have nothing to resolve. If you'd rather it go the other way, say so.

AI-assisted: yes (Claude Code).

@JJenkx

JJenkx commented Oct 28, 2026

Copy link
Copy Markdown
Contributor

@UnhealthyKraken a merge-order question: a maintainer asked the authors of #12514 (swscanf floating fields as titles' libc.prx does) and of the PRs it overlaps to agree an order. The only overlap with this PR is in docs/dev/debt/libc.md: git merge-tree reports a textual conflict between the two PRs' edits to nearby debt entries. The code doesn't overlap.

Proposed order: this PR lands first, and #12514 rebases afterwards (#12514 will declare it in Depends on). Your PR needs no changes. Could you confirm that order works for you, or say if you'd rather #12514 went first?

AI-assisted: yes (Claude Code).

@MarcZX10 MarcZX10 left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Re-checked — changes requested

The zero-capacity short-field finding from my earlier review is resolved: the tests now pin the measured assignment count/output/errno behavior, the stale debt sentence is removed, and the author reports focused Linux and Windows runs on the current feature head. I found no new implementation defect in that fix.

Two readiness items remain. First, the #12420 author proposed #9863 first, and the #12514 author independently proposed the same order for the debt-file overlap. Please confirm that order so the follow-up authors can record their dependencies. Second, current main has advanced since this branch’s last merge; docs/dev/debt/libc.md changed on both sides, even though the merge preview is currently clean. Please reconcile the debt entry against current main and rerun the documented checks on the integrated head.

The focused scanner tests and policy checks are reported green; I did not run them locally. This request is for the unconfirmed overlap order and current-main integration, not the resolved zero-capacity behavior.

@github-actions github-actions Bot added needs rebase Conflicts with main, rebase needed and removed needs rebase Conflicts with main, rebase needed labels Nov 1, 2026
docs/dev/debt/libc.md: keep this branch's swscanf_s changes and take main's new _WStoul sentence (a bad base returns 0, as Dinkumware's xstoul.c does).
@github-actions github-actions Bot removed the needs rebase Conflicts with main, rebase needed label Nov 2, 2026
# Conflicts:
#	core/libs/tests/GuestWideStreamScan.cpp
@oneandonlydean
oneandonlydean merged commit 238a13d into boykopovar:main Nov 4, 2026
19 of 20 checks passed
orezraey added a commit to orezraey/AnyPS5 that referenced this pull request Nov 4, 2026
Take main's set_constraint_handler_s and wcsncat_s entries and boykopovar#9863's short-field
wording, keep this branch's sscanf_s constraint wording, and use SonyRsizeMax
from SonyCrt.hpp instead of a local copy of the same limit.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

7 participants