summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFather Chrysostomos <sprout@cpan.org>2011-05-30 09:49:36 -0700
committerFather Chrysostomos <sprout@cpan.org>2011-05-30 09:49:36 -0700
commit8fe85e3fe48130bc5b95139890db97fc7a6c2c49 (patch)
tree394c2336ee5c558365078306c9ecba6a6b76df92
parentd34a666494db40538f88613ec991214f3a862865 (diff)
downloadperl-8fe85e3fe48130bc5b95139890db97fc7a6c2c49.tar.gz
[perl #31946] Warn when assigning to a TEMP
This is the first step in downgrading a fatal error (Can't return a temporary from lvalue subroutine) to a warning. Currently only XS lvalue routines that return TEMPs and pure-Perl lvalue routines that use explicit return (which don’t quite work properly yet anyway, despite commit fa1e92c) are affected by this. This is implemented in pp_sassign and pp_aassign, rather than pp_leavesublv, so it will affect explicit returns and so it will be skipped for overloaded ‘.=’, etc. Thanks to Craig DeForest for suggesting how to do this.
-rw-r--r--pod/perldiag.pod6
-rw-r--r--pp_hot.c7
2 files changed, 13 insertions, 0 deletions
diff --git a/pod/perldiag.pod b/pod/perldiag.pod
index b90a141961..39393d8fd2 100644
--- a/pod/perldiag.pod
+++ b/pod/perldiag.pod
@@ -4974,6 +4974,12 @@ See L<POSIX/FUNCTIONS> for more information.
(F) You called a Win32 function with incorrect arguments.
See L<Win32> for more information.
+=item Useless assignment to a temporary
+
+(W misc) You assigned to an lvalue subroutine, but what
+the subroutine returned was a temporary scalar about to
+be discarded, so the assignment had no effect.
+
=item Useless (?-%s) - don't use /%s modifier in regex; marked by <-- HERE in m/%s/
(W regexp) You have used an internal modifier such as (?-o) that has no
diff --git a/pp_hot.c b/pp_hot.c
index 531a33e219..04de368d18 100644
--- a/pp_hot.c
+++ b/pp_hot.c
@@ -197,6 +197,13 @@ PP(pp_sassign)
}
}
+ if (
+ SvTEMP(right) && !SvSMAGICAL(right) && SvREFCNT(right) == 1 &&
+ (!isGV_with_GP(right) || SvFAKE(right)) && ckWARN(WARN_MISC)
+ )
+ Perl_warner(aTHX_
+ packWARN(WARN_MISC), "Useless assignment to a temporary"
+ );
SvSetMagicSV(right, left);
SETs(right);
RETURN;