From 36006093557016bee8943d68d0c72eac6ebb392e Mon Sep 17 00:00:00 2001 From: "Flavio S. Glock" Date: Thu, 29 Oct 2026 16:28:53 +0100 Subject: [PATCH] fix: preserve names on copied stash globs Keep the source name as display metadata when copying package stash entries into ordinary hashes. Detached slot lookup remains independent from the live package stash. Add standard-Perl-validated regression coverage and verify Carp::Notify 1.13 on JVM and interpreter backends. Fixes #1927. Generated with [Codex](https://openai.com/codex) Co-Authored-By: Codex --- docs/about/changelog.md | 2 ++ .../runtime/runtimetypes/RuntimeStash.java | 3 +++ .../unit/stash_copied_glob_stringification.t | 12 ++++++++++++ 3 files changed, 17 insertions(+) create mode 100644 src/test/resources/unit/stash_copied_glob_stringification.t diff --git a/docs/about/changelog.md b/docs/about/changelog.md index 374ddc53dc..3889964e81 100644 --- a/docs/about/changelog.md +++ b/docs/about/changelog.md @@ -6,6 +6,8 @@ priorities and future plans. ## Work in progress +- Preserve named typeglob stringification when copying package stash entries (#1927). + - Reduce repeated eval STRING overhead with lazy state and caching for context-free integer-literal evals (#1911). - Preserve arbitrary bytes in SQLite text columns across DBI fetches (#1923). diff --git a/src/main/java/org/perlonjava/runtime/runtimetypes/RuntimeStash.java b/src/main/java/org/perlonjava/runtime/runtimetypes/RuntimeStash.java index 0c26546dc2..b6733bf066 100644 --- a/src/main/java/org/perlonjava/runtime/runtimetypes/RuntimeStash.java +++ b/src/main/java/org/perlonjava/runtime/runtimetypes/RuntimeStash.java @@ -622,6 +622,9 @@ private static RuntimeScalar snapshotStashEntry(String key, RuntimeScalar value) RuntimeGlob io = GlobalVariable.peekGlobalIO(sourceName); RuntimeScalar code = GlobalVariable.globalCodeRefs.get(sourceName); RuntimeGlob snapshot = RuntimeGlob.createDetachedWithSlots(scalar, array, hash, io, code); + // A detached glob has no live stash name for slot access, but a Perl + // typeglob copied out of a stash still stringifies with its source name. + snapshot.setStringificationName(sourceName); return new RuntimeScalar(snapshot); } diff --git a/src/test/resources/unit/stash_copied_glob_stringification.t b/src/test/resources/unit/stash_copied_glob_stringification.t new file mode 100644 index 0000000000..bafe45454d --- /dev/null +++ b/src/test/resources/unit/stash_copied_glob_stringification.t @@ -0,0 +1,12 @@ +use strict; +use warnings; +use Test::More tests => 1; + +{ + package StashCopiedGlobStringification; + sub exported { 1 } +} + +my %stash = %StashCopiedGlobStringification::; +is("$stash{exported}", '*StashCopiedGlobStringification::exported', + 'a glob copied from a package stash retains its name when stringified');