www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.announce - Function Hijacking article

reply Walter Bright <newshound1 digitalmars.com> writes:
http://www.digitalmars.com/d/hijack.html

(this is what my talk at NWCPP will be on tonight)

Digg: http://digg.com/programming/Function_Hijacking_Mitigation
Reddit: http://programming.reddit.com/new
Oct 17 2007
next sibling parent Lutger <lutger.blijdestijn gmail.com> writes:
Walter Bright wrote:
 http://www.digitalmars.com/d/hijack.html
 
 (this is what my talk at NWCPP will be on tonight)
 
 Digg: http://digg.com/programming/Function_Hijacking_Mitigation
 Reddit: http://programming.reddit.com/new

Good stuff! Could you add a link to the article section so people who don't read the newsgroup will find it?
Oct 17 2007
prev sibling next sibling parent Matti Niemenmaa <see_signature for.real.address> writes:
Walter Bright wrote:
 http://www.digitalmars.com/d/hijack.html
 
 (this is what my talk at NWCPP will be on tonight)
 
 Digg: http://digg.com/programming/Function_Hijacking_Mitigation
 Reddit: http://programming.reddit.com/new

Nice article, and thanks for D's clean solution to the issue. The exact Reddit link: http://programming.reddit.com/info/5yje3/comments/ -- E-mail address: matti.niemenmaa+news, domain is iki (DOT) fi
Oct 18 2007
prev sibling next sibling parent reply "Stewart Gordon" <smjg_1998 yahoo.com> writes:
"Walter Bright" <newshound1 digitalmars.com> wrote in message 
news:ff61om$bis$1 digitalmars.com...
 http://www.digitalmars.com/d/hijack.html

<snip> "B.vtbl[0] = &B.foo(long); B.vtbl[1] = &error;" So the compiler generates an override that throws a runtime error? Does it apply to all overloads, or only where potentially compatible parameter types are involved? Stewart. -- My e-mail address is valid but not my primary mailbox. Please keep replies on the 'group where everybody may benefit.
Oct 18 2007
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Stewart Gordon wrote:
 http://www.digitalmars.com/d/hijack.html

<snip> "B.vtbl[0] = &B.foo(long); B.vtbl[1] = &error;" So the compiler generates an override that throws a runtime error?

Yes.
 Does 
 it apply to all overloads, or only where potentially compatible 
 parameter types are involved?

It applies to virtual functions that exist in the vtbl[], but are inaccessible via anything typed with the derived class.
Oct 18 2007
parent reply "Stewart Gordon" <smjg_1998 yahoo.com> writes:
"Walter Bright" <newshound1 digitalmars.com> wrote in message 
news:ff7req$28lq$1 digitalmars.com...
 Stewart Gordon wrote:

 So the compiler generates an override that throws a runtime error?

Yes.

I see now. But function.html is out of date - the second example under "Function Inheritance and Overriding" is now bogus. And I noticed that the requirement to specify the override attribute is neither implemented nor documented under attribute.html - what gives?
 Does it apply to all overloads, or only where potentially compatible 
 parameter types are involved?

It applies to virtual functions that exist in the vtbl[], but are inaccessible via anything typed with the derived class.

But if there's no chance of calling one intending the other, e.g. class Qwert { void yuiop(int i) { writefln("Qwert.yuiop: int %d", i); } void yuiop(string s) { writefln("Qwert.yuiop: string %s", s); } } class Asdfg : Qwert { override void yuiop(string s) { writefln("Asdfg.yuiop: string %s", s); } } should it still count? Stewart. -- My e-mail address is valid but not my primary mailbox. Please keep replies on the 'group where everybody may benefit.
Oct 18 2007
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Stewart Gordon wrote:
 "Walter Bright" <newshound1 digitalmars.com> wrote in message 
 news:ff7req$28lq$1 digitalmars.com...
 Stewart Gordon wrote:

 So the compiler generates an override that throws a runtime error?

Yes.

I see now. But function.html is out of date - the second example under "Function Inheritance and Overriding" is now bogus.

I'll fix that.
 And I noticed that 
 the requirement to specify the override attribute is neither implemented 
 nor documented under attribute.html - what gives?

It is documented in the function.html and attribute.html. It is implemented if you add the -w switch.
 
 Does it apply to all overloads, or only where potentially compatible 
 parameter types are involved?

It applies to virtual functions that exist in the vtbl[], but are inaccessible via anything typed with the derived class.

But if there's no chance of calling one intending the other, e.g. class Qwert { void yuiop(int i) { writefln("Qwert.yuiop: int %d", i); } void yuiop(string s) { writefln("Qwert.yuiop: string %s", s); } } class Asdfg : Qwert { override void yuiop(string s) { writefln("Asdfg.yuiop: string %s", s); } } should it still count?

Yes, because Qwert can have a function which calls yuiop(int) with an Asdfg instance.
Oct 18 2007
parent reply "Stewart Gordon" <smjg_1998 yahoo.com> writes:
"Walter Bright" <newshound1 digitalmars.com> wrote in message 
news:ff8fi1$fs7$1 digitalmars.com...
 Stewart Gordon wrote:

 And I noticed that the requirement to specify the override attribute is 
 neither implemented nor documented under attribute.html - what gives?

It is documented in the function.html and attribute.html.

I still can't find it anywhere.
 It is implemented if you add the -w switch.

I see.... <snip>
 But if there's no chance of calling one intending the other, e.g.

 class Qwert {
    void yuiop(int i)    { writefln("Qwert.yuiop: int %d", i); }
    void yuiop(string s) { writefln("Qwert.yuiop: string %s", s); }
 }

 class Asdfg : Qwert {
    override void yuiop(string s) { writefln("Asdfg.yuiop: string %s", 
 s); }
 }

 should it still count?

Yes, because Qwert can have a function which calls yuiop(int) with an Asdfg instance.

I'm not with you. How exactly does this render my example susceptible to the hijacking problem? Stewart. -- My e-mail address is valid but not my primary mailbox. Please keep replies on the 'group where everybody may benefit.
Oct 18 2007
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Stewart Gordon wrote:
 "Walter Bright" <newshound1 digitalmars.com> wrote in message 
 news:ff8fi1$fs7$1 digitalmars.com...
 Stewart Gordon wrote:

 And I noticed that the requirement to specify the override attribute 
 is neither implemented nor documented under attribute.html - what gives?

It is documented in the function.html and attribute.html.

I still can't find it anywhere.

In attribute.html, click on "override" under "Attribute" in the grammar section. In function.html, search for "override".
 
 It is implemented if you add the -w switch.

I see.... <snip>
 But if there's no chance of calling one intending the other, e.g.

 class Qwert {
    void yuiop(int i)    { writefln("Qwert.yuiop: int %d", i); }
    void yuiop(string s) { writefln("Qwert.yuiop: string %s", s); }
 }

 class Asdfg : Qwert {
    override void yuiop(string s) { writefln("Asdfg.yuiop: string %s", 
 s); }
 }

 should it still count?

Yes, because Qwert can have a function which calls yuiop(int) with an Asdfg instance.

I'm not with you. How exactly does this render my example susceptible to the hijacking problem?

If Qwert defines a function def: void def() { yuiop(1); }
Oct 18 2007
parent reply "Stewart Gordon" <smjg_1998 yahoo.com> writes:
"Walter Bright" <newshound1 digitalmars.com> wrote in message 
news:ff8qto$1k6r$2 digitalmars.com...
 Stewart Gordon wrote:
 "Walter Bright" <newshound1 digitalmars.com> wrote in message 
 news:ff8fi1$fs7$1 digitalmars.com...
 Stewart Gordon wrote:

 And I noticed that the requirement to specify the override attribute is 
 neither implemented nor documented under attribute.html - what gives?

It is documented in the function.html and attribute.html.

I still can't find it anywhere.

In attribute.html, click on "override" under "Attribute" in the grammar section.

I already did. I get this: "The override attribute applies to virtual functions. It means that the function must override a function with the same name and parameters in a base class. The override attribute is useful for catching errors when a base class's member function gets its parameters changed, and all derived classes need to have their overriding functions updated." followed by a code example that demonstrates this. So it states that the override attribute _may_ be used if it overrides, and _must not_ be used if it doesn't override. I can't see anything there that relates to a circumstance in which the override attribute _must_ be used to make the code compile. What am I missing?
 In function.html, search for "override".

I already did. The only hits either don't address the question of required or not, or blatantly violate the requirement. <snip>
 I'm not with you.  How exactly does this render my example susceptible to 
 the hijacking problem?

If Qwert defines a function def: void def() { yuiop(1); }

You state that this particular form of hijacking problem occurs because a call originally to yuiop(long) becomes a call to yuiop(int) when such a method is added to the base class. But since yuiop(1) can never have possibly been a call to any yuiop(string), why is it a problem? It's true that the creator of class Qwert could have changed the call in Qwert.def, e.g. from yuiop("1") to yuiop(1). But it's equally possible that the new method with an int parameter could have been given a completely different name, and def changed to call that. Indeed, if two function signatures can never be matched by identical-looking argument lists, UIMS it makes no difference whether the functions have the same name or not. Stewart. -- My e-mail address is valid but not my primary mailbox. Please keep replies on the 'group where everybody may benefit.
Oct 18 2007
parent reply Reiner Pope <some address.com> writes:
Stewart Gordon wrote:
 "Walter Bright" <newshound1 digitalmars.com> wrote in message 
 news:ff8qto$1k6r$2 digitalmars.com...
 Stewart Gordon wrote:
 "Walter Bright" <newshound1 digitalmars.com> wrote in message 
 news:ff8fi1$fs7$1 digitalmars.com...
 Stewart Gordon wrote:

 And I noticed that the requirement to specify the override 
 attribute is neither implemented nor documented under 
 attribute.html - what gives?

It is documented in the function.html and attribute.html.

I still can't find it anywhere.

In attribute.html, click on "override" under "Attribute" in the grammar section.

I already did. I get this: "The override attribute applies to virtual functions. It means that the function must override a function with the same name and parameters in a base class. The override attribute is useful for catching errors when a base class's member function gets its parameters changed, and all derived classes need to have their overriding functions updated." followed by a code example that demonstrates this. So it states that the override attribute _may_ be used if it overrides, and _must not_ be used if it doesn't override. I can't see anything there that relates to a circumstance in which the override attribute _must_ be used to make the code compile. What am I missing?
 In function.html, search for "override".

I already did. The only hits either don't address the question of required or not, or blatantly violate the requirement. <snip>
 I'm not with you.  How exactly does this render my example 
 susceptible to the hijacking problem?

If Qwert defines a function def: void def() { yuiop(1); }

You state that this particular form of hijacking problem occurs because a call originally to yuiop(long) becomes a call to yuiop(int) when such a method is added to the base class. But since yuiop(1) can never have possibly been a call to any yuiop(string), why is it a problem?

I suppose this could cause problems: struct S { string opImplicitCastTo() {...} int opImplicitCastTo() {...} } ... yuiop( S() ) -- Reiner
Oct 18 2007
parent "Stewart Gordon" <smjg_1998 yahoo.com> writes:
"Reiner Pope" <some address.com> wrote in message 
news:ff93tt$20hm$1 digitalmars.com...
<snip excessive quote>
 I suppose this could cause problems:

 struct S
 {
     string opImplicitCastTo() {...}
     int opImplicitCastTo() {...}
 }
 ...
 yuiop( S() )

Is this (still) in the pipeline? I'm still not sure about it. See my comment at http://tinyurl.com/2kesmr Stewart. -- My e-mail address is valid but not my primary mailbox. Please keep replies on the 'group where everybody may benefit.
Oct 19 2007
prev sibling parent reply Aarti_pl <aarti interia.pl> writes:
Walter Bright pisze:
 http://www.digitalmars.com/d/hijack.html
 
 (this is what my talk at NWCPP will be on tonight)
 
 Digg: http://digg.com/programming/Function_Hijacking_Mitigation
 Reddit: http://programming.reddit.com/new

Very nice article! Just please add inheritance (': A') in "Derived Class Member Function Hijacking #2", which is missing currently. I finally got completely convinced for D inheritance way :-) I noticed also in my implementation of ProgramOptions that such a behavior allows to hide base class implementation, making it possible to make better structured programs, compile time checked for functions usage: // General base class class A { // General implementation good for most of subclasses void opCall(int a, int b, int c) {} } // Specific implementation class B : A { // Specific implementation for this class // Calling general implementation should not be allowed void opCall(char[] text) {} } Now you have compile time checking for B.opCall() and hidden base class methods opCall(). Really sweet! BR Marcin Kuszczak (aarti_pl - www.zapytajmnie.com)
Oct 18 2007
parent reply Walter Bright <newshound1 digitalmars.com> writes:
Aarti_pl wrote:
 Just please add inheritance (': A') in "Derived Class Member Function 
 Hijacking #2", which is missing currently.

Fixed!
Oct 18 2007
parent reply Aarti_pl <aarti interia.pl> writes:
Walter Bright pisze:
 Aarti_pl wrote:
 Just please add inheritance (': A') in "Derived Class Member Function 
 Hijacking #2", which is missing currently.

Fixed!

Only in one place... There are still two places with same bug, few lines below :D BR Marcin Kuszczak
Oct 18 2007
parent Walter Bright <newshound1 digitalmars.com> writes:
Aarti_pl wrote:
 Walter Bright pisze:
 Aarti_pl wrote:
 Just please add inheritance (': A') in "Derived Class Member Function 
 Hijacking #2", which is missing currently.

Fixed!

Only in one place... There are still two places with same bug, few lines below :D

Argh!
Oct 18 2007