Pitfalls of delegates inside ranges

Artur Skawina art.08.09 at gmail.com
Mon Sep 2 10:31:02 PDT 2013


On 09/02/13 18:32, Joseph Rushton Wakeling wrote:
> On 02/09/13 17:44, Artur Skawina wrote:
>> The nasty part of that is that the type of .funcptr, hence also of the
>> '_jump' pointer, is bogus. So calling via '_jump' directly can succeed,
>> but do the wrong thing. It's a language issue; one reasonable workaround
>> would be to define a MemberPtr type, which disallows direct calls.
> 
> SafeDelegate, perhaps?  Might be a worthwhile library addition.

"Fixing" type system bugs by adding library helpers is not really a good
idea. '.funcptr' returning incorrect type (and 'typeof(T.method)' etc)
needs to be fixed properly. Until that happens, the alternatives are:
a) convention - don't directly access these wrongly-typed pointers;
b) cast to (void*) (or the correct type) and back; ugly and still un at safe;
c) wrap the pointer, this way it's at least a little bit harder to
   mistakenly use the bogus type.

The last alternative could look similar to:

   struct MemberFunc(MF, T, DG) {
      MF mf;
      auto ref opCall(A...)(ref T o, auto ref A a) {
         DG dg = void; dg.ptr = &o; dg.funcptr = mf; return dg(a);
      }
   }

   auto memberFunc(T, DG)(ref T, DG dg) {
      auto fp = dg.funcptr;
      MemberFunc!(typeof(fp), T, DG) r /*@unsafe: = void*/;
      r.mf = fp;
      return r;
   }

   struct S {
      int a;
      double f(int b) { return a+b; }
   }

   void main() {
      auto s = S(3);
      auto mp = memberFunc(s, &s.f);
      mp(s, 5);
      auto s2 = S(4);
      mp(s2, 5);
   }

artur


More information about the Digitalmars-d-learn mailing list