www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - Error: 'this' is only defined in non-static member functions, not main

reply "remi thebault" <remi.thebault outlook.com> writes:
Hello

I have this weird error trying to achieve something simple:


module list_test;

// import wayland.util;


template Id(alias a) { alias Id = a; }


template ParentOf(alias member)
{
     alias ParentOf = Id!(__traits(parent, member));
}


template wl_container_of(alias member)
{
     ParentOf!(member)*
     get(wl_list* ptr)
     {
         return 
cast(ParentOf!(member)*)(cast(ptrdiff_t)(ptr)-member.offsetof);
     }
}


struct wl_list {
     wl_list *prev;
     wl_list *next;
}


struct item {
     int num;
     wl_list link;

     this(int num) {
         this.num = num;
     }
}

int main (string[] args)
{
     auto i1 = item(1);
     auto i2 = item(2);
     auto i3 = item(3);

     wl_list lst;
//     wl_list_init(&lst);
//     wl_list_insert(&lst, &i1.link);
//     wl_list_insert(&lst, &i2.link);
//     wl_list_insert(&i2.link, &i3.link);

     item *it = wl_container_of!(item.link).get(&i2.link); // 
error on this line

     return 0;
}


If I change the definition of wl_container_of to:
template wl_container_of(alias member)
{
     ParentOf!(member)*
     wl_container_of(wl_list* ptr)
     {
         return 
cast(ParentOf!(member)*)(cast(ptrdiff_t)(ptr)-member.offsetof);
     }
}

and call to:
wl_container_of!(item.link)(&i2.link);

I now get a different error:
Error: need 'this' for 'wl_container_of' of type 'pure nothrow 
 nogc  system item*(wl_list* ptr)'


I run dmd v2.067 on linux 64bits.

Any idea?

thanks
RĂ©mi
Jul 29 2015
parent reply "anonymous" <anonymous example.com> writes:
On Wednesday, 29 July 2015 at 21:33:16 UTC, remi thebault wrote:
 Hello

 I have this weird error trying to achieve something simple:
That's far from simple. Here's a reduction: ---- template wl_container_of(alias member) { size_t get() {return member.offsetof;} } struct item { int link; } void main() { wl_container_of!(item.link).get(); /* Error: 'this' is only defined in non-static member functions, not main */ } ---- I'm not sure what's going on here, if this should or shouldn't work. The error message isn't exactly good. Slapping `static` on `get` seems to make it work: ---- static size_t get() {return member.offsetof;} ---- I guess the compiler thinks that since `item.link` is an instance member, it needs a `this`. And then `get` would need a `this` too as it's using `item.link` via `member`. When the compiler sees that there is no `this`, it errors out. An explicit `static` forces the compiler to assume no `this`. And it would error out if you actually tried to make use of it. Naively, I'd think the compiler should be able to figure that out itself.
Jul 29 2015
parent "remi thebault" <remi.thebault outlook.com> writes:
On Wednesday, 29 July 2015 at 22:12:38 UTC, anonymous wrote:
 Slapping `static` on `get` seems to make it work:
 ----
     static size_t get() {return member.offsetof;}
 ----
Good slap, thanks! you solved my problem
 I guess the compiler thinks that since `item.link` is an 
 instance member, it needs a `this`. And then `get` would need a 
 `this` too as it's using `item.link` via `member`. When the 
 compiler sees that there is no `this`, it errors out.

 An explicit `static` forces the compiler to assume no `this`. 
 And it would error out if you actually tried to make use of it.

 Naively, I'd think the compiler should be able to figure that 
 out itself.
I guess that is a dmd bug. I'll fill a report in case of.
Jul 29 2015