Thread overview
template instance cannot use local 'f' as parameter to non-global template
Jul 12, 2011
Trass3r
Jul 13, 2011
Trass3r
Jul 13, 2011
Stephan
Jul 13, 2011
Trass3r
Jul 13, 2011
Tyro[a.c.edwards]
Jul 13, 2011
Trass3r
Jul 14, 2011
Tyro[a.c.edwards]
Jul 13, 2011
Trass3r
July 12, 2011
Is this a bug? If not, how do you make it work?

void h() {}

class Bla
{
	mixin wrap!h;
}

mixin template wrap(alias f)
{
	void blub(alias g = f)()
	{
	}
}

void main()
{
	Bla b = new Bla();
	b.blub();
}

test.d(18): Error: template instance cannot use local 'f' as parameter to non-global template blub(alias g = f)
test.d(18): Error: template instance forward reference of f
test.d(18): Error: template instance test.Bla.wrap!(h).blub!(f) error instantiating
July 13, 2011
Anybody an idea?
July 13, 2011
On 12.07.2011 15:06, Trass3r wrote:
> Is this a bug? If not, how do you make it work?
>
> void h() {}
>
> class Bla
> {
> mixin wrap!h;
> }
>
> mixin template wrap(alias f)
> {
> void blub(alias g = f)()
> {
> }
> }
>
> void main()
> {
> Bla b = new Bla();
> b.blub();
> }
>
> test.d(18): Error: template instance cannot use local 'f' as parameter
> to non-global template blub(alias g = f)
> test.d(18): Error: template instance forward reference of f
> test.d(18): Error: template instance test.Bla.wrap!(h).blub!(f) error
> instantiating

I am not sure but i am not that used to those template aliases anyway.
July 13, 2011
On Tue, 12 Jul 2011 09:06:56 -0400, Trass3r <un@known.com> wrote:

> Is this a bug? If not, how do you make it work?
>
> void h() {}
>
> class Bla
> {
> 	mixin wrap!h;
> }
>
> mixin template wrap(alias f)
> {
> 	void blub(alias g = f)()
> 	{
> 	}
> }
>
> void main()
> {
> 	Bla b = new Bla();
> 	b.blub();
> }
>
> test.d(18): Error: template instance cannot use local 'f' as parameter to non-global template blub(alias g = f)
> test.d(18): Error: template instance forward reference of f
> test.d(18): Error: template instance test.Bla.wrap!(h).blub!(f) error instantiating

I've seen this error before...

*searches memory and old code*

Here you go: http://d.puremagic.com/issues/show_bug.cgi?id=3051

As a workaround, is there a reason you need blub to be parameterized?  I mean, f is already part of the template.

-Steve
July 13, 2011
Am 13.07.2011, 16:02 Uhr, schrieb Steven Schveighoffer <schveiguy@yahoo.com>:

>> void h() {}
>>
>> class Bla
>> {
>> 	mixin wrap!h;
>> }
>>
>> mixin template wrap(alias f)
>> {
>> 	void blub(alias g = f)()
>> 	{
		g();
>> 	}
>> }

> As a workaround, is there a reason you need blub to be parameterized?  I mean, f is already part of the template.

Yep, a default function is passed to wrap and in most cases blub just calls that one.
But sometimes I need blub to use a function other than the default one.
July 13, 2011
On 7/13/2011 11:35 PM, Trass3r wrote:
> Am 13.07.2011, 16:02 Uhr, schrieb Steven Schveighoffer
> <schveiguy@yahoo.com>:
>
>>> void h() {}
>>>
>>> class Bla
>>> {
>>> mixin wrap!h;
>>> }
>>>
>>> mixin template wrap(alias f)
>>> {
>>> void blub(alias g = f)()
>>> {
> g();
>>> }
>>> }
>
>> As a workaround, is there a reason you need blub to be parameterized?
>> I mean, f is already part of the template.
>
> Yep, a default function is passed to wrap and in most cases blub just
> calls that one.
> But sometimes I need blub to use a function other than the default one.

Don't know it this is the right answer or a possible bug but it does the trick:

void h() { import std.stdio; write("h()"); }

class Bla
{
    mixin wrap!h;
}

mixin template wrap(alias f)
{
    void blub(typeof(&f) g = &f)
    {
    	g();
    }
}

void main()
{
    Bla b = new Bla();
    b.blub();
}
July 13, 2011
Am 13.07.2011, 16:58 Uhr, schrieb Tyro[a.c.edwards] <nospam@home.com>:
> Don't know it this is the right answer or a possible bug but it does the trick:
>
> void h() { import std.stdio; write("h()"); }
>
> class Bla
> {
>      mixin wrap!h;
> }
>
> mixin template wrap(alias f)
> {
>      void blub(typeof(&f) g = &f)
>      {
>      	g();
>      }
> }
>
> void main()
> {
>      Bla b = new Bla();
>      b.blub();
> }

Thanks!
Unfortunately it doesn't work with more complex functions:

Error: arithmetic/string type expected for value-parameter, not cl_errcode C function(cl_program program, uint param_name, ulong param_value_size, void* param_value, ulong* param_value_size_ret)
July 13, 2011
> I've seen this error before...
>
> *searches memory and old code*
>
> Here you go: http://d.puremagic.com/issues/show_bug.cgi?id=3051

I think this is yet another issue.
The inner template argument is not something on the stack but it is a template argument.
July 14, 2011
On 7/14/2011 12:24 AM, Trass3r wrote:
> Am 13.07.2011, 16:58 Uhr, schrieb Tyro[a.c.edwards] <nospam@home.com>:
>> Don't know it this is the right answer or a possible bug but it does
>> the trick:
>>
>> void h() { import std.stdio; write("h()"); }
>>
>> class Bla
>> {
>> mixin wrap!h;
>> }
>>
>> mixin template wrap(alias f)
>> {
>> void blub(typeof(&f) g = &f)
>> {
>> g();
>> }
>> }
>>
>> void main()
>> {
>> Bla b = new Bla();
>> b.blub();
>> }
>
> Thanks!
> Unfortunately it doesn't work with more complex functions:
>
> Error: arithmetic/string type expected for value-parameter, not
> cl_errcode C function(cl_program program, uint param_name, ulong
> param_value_size, void* param_value, ulong* param_value_size_ret)

I guess the simplest example of the problem you're experiencing would be this:

void h() { import std.stdio; write("h()"); }

void function() fp = &h;

class Bla
{
    mixin wrap!(fp);
}

mixin template wrap(alias f)
{
    void blub()
    {
        typeof(&f) g = &f;
    g();  // <--- source of error [1]
    }
}

void main()
{
    Bla b = new Bla();
    b.blub();
}

edit1.d(19): Error: function expected before (), not g of type void function()*

[1] Here you are calling a function pointer which simply returns the address of the function... hence your error!

Try calling the function pointed to by differencing the pointer as such: (*g)() and your problem is solved.