Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:85382 Return-Path: Mailing-List: contact internals-help@lists.php.net; run by ezmlm Delivered-To: mailing list internals@lists.php.net Received: (qmail 80274 invoked from network); 21 Mar 2015 17:56:09 -0000 Received: from unknown (HELO lists.php.net) (127.0.0.1) by localhost with SMTP; 21 Mar 2015 17:56:09 -0000 Authentication-Results: pb1.pair.com smtp.mail=contact@geolim4.com; spf=pass; sender-id=pass Authentication-Results: pb1.pair.com header.from=contact@geolim4.com; sender-id=pass Received-SPF: pass (pb1.pair.com: domain geolim4.com designates 212.129.18.216 as permitted sender) X-PHP-List-Original-Sender: contact@geolim4.com X-Host-Fingerprint: 212.129.18.216 houblon.geolim4.com Received: from [212.129.18.216] ([212.129.18.216:34467] helo=houblon.geolim4.com) by pb1.pair.com (ecelerity 2.1.1.9-wez r(12769M)) with ESMTP id E8/4B-18917-7B0BD055 for ; Sat, 21 Mar 2015 12:56:08 -0500 Received: from mail-qc0-f176.google.com (mail-qc0-f176.google.com [209.85.216.176]) (Authenticated sender: contact@geolim4.com) by houblon.geolim4.com (Postfix) with ESMTPSA id 5AD6EEC0AD6 for ; Sat, 21 Mar 2015 18:56:03 +0100 (CET) Received: by qcay5 with SMTP id y5so26925065qca.1 for ; Sat, 21 Mar 2015 10:56:02 -0700 (PDT) X-Received: by 10.140.31.116 with SMTP id e107mr105126750qge.36.1426960562362; Sat, 21 Mar 2015 10:56:02 -0700 (PDT) MIME-Version: 1.0 Received: by 10.140.90.36 with HTTP; Sat, 21 Mar 2015 10:55:32 -0700 (PDT) In-Reply-To: <3136D99B-EA3D-4AF1-9B20-C13DF55E3A53@zort.net> References: <3136D99B-EA3D-4AF1-9B20-C13DF55E3A53@zort.net> Date: Sat, 21 Mar 2015 18:55:32 +0100 Message-ID: To: John Bafford Cc: Benjamin Eberlei , PHP Internals Content-Type: multipart/alternative; boundary=001a113a95446da32f0511d02502 Subject: Re: [PHP-DEV] RFC: Nested enclosing returns From: contact@geolim4.com ("Georges.L") --001a113a95446da32f0511d02502 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: quoted-printable To be honest I had not thought about the bad side of this use, i guess it could be possible to not return upper than a try/catch block (then return a fatal error if our code is trying to returns upper than a try/catch block). Now the practical example: // Code i have the hand on function main() { foo('bar'); echo "I'm an angel !"; } function bar() { echo "I'm not Evil"; } //Code i don't have the hand on (like a MVC core) function foo($thing) { // make_love_dont_war(); call_user_func($thing); //Do some stuff i don't want to execute echo 'evil'; } function make_love_dont_war() { echo 'Make love, dont war.'; } You get it ? Georges.L 2015-03-21 17:07 GMT+01:00 John Bafford : > > On Mar 21, 2015, at 10:17, Georges.L wrote: > > > The main purpose of this RFC is *not* to improve the exception system o= f > > PHP but to improve the code logic/hierarchy. > > > >>> Hi php internals, > >>> > >>> After some long and deep research i finally decided to write my first > RFC > >>> about a feature i'd be interested to be improved in the php core: > *Nested > >>> enclosing returns* > > Georges, > > This would make simply looking at code and reasoning about what it does > impossible. > > At present, if I have the following code: > > function foo() { > if(doSomething()) { > success(); > } else { > failure(); > } > > return 42; > } > > try { > bar(foo()); > } catch($ex) { > } > > Then I can make the following true statements about this code: > * foo always calls doSomething() > * foo always calls either success() or failure(), based on the > result of doSomething() > * foo always returns 42 > * bar is always called (with foo=E2=80=99s return value, 42) > * Alternatively to the above, any of the called functions may > throw an exception, which will be caught by the catch block > > If any of doSomething(), success(), failure(), or bar() can arbitrarily > return to some higher calling scope, then the only thing I can say for su= re > is that doSomething() is called, after which my application could be in > some dangerously inconsistent state because I have no idea what will be > executed next. > > This then provides significant security concerns. For example, if we have > this: > > function API_Function_With_Callback($callback) { > try { > $callback(); > > //do more stuff > > return true; > } catch($ex) { > //do error stuff > > return false; > } > } > > function doEvil() { > $sentinel =3D //some unique value > > $result =3D API_Function_With_Callback(function() use($sentinel) = { > $backtrace =3D debug_backtrace(); > $nestingLevel =3D //determine nesting level from backtrac= e > if($nestingLevel =3D=3D 2) return $sentinel, 2; > else if($nestingLevel =3D=3D 3) return $sentinel, 3; > else if($nestingLevel =3D=3D 4) return $sentinel, 4; > // etc > } > > // Exploit inconsistent state of Call_API_Function here > if($result =3D=3D=3D $sentinel) { =E2=80=A6 } > } > > Then we can short-circuit code from some other library which isn=E2=80=99= t > prepared to deal with this kind of hijacking. More seriously, this sort o= f > hijacking *can=E2=80=99t* be defended against (at least not without a wea= kening of > your original proposal). Any function that takes a callback is potentiall= y > vulnerable to this sort of attack. > > > Can you suggest an actual, practical, example, where this would be such a > benefit as to override the inherent difficulty about reasoning about this > code, and the potential security concerns? Are there any other languages > that make something like this possible? > > I suspect that any code that could be =E2=80=9Cimproved=E2=80=9D with thi= s functionality > is already in significant need of improvement by more conventional means. > > -John > > --001a113a95446da32f0511d02502--