DIP 50 - AST macros

Jacob Carlborg doob at me.com
Wed Nov 13 23:50:55 PST 2013


On 2013-11-14 02:56, deadalnix wrote:

> I think the whole point of macro is to NOT add too much feature to the
> language.
>
> See for instance the example I gave before to create generator. This can
> be added with extra language support (C# async/await is an example). But
> with macro, the feature can be implemented as a library.
>
> It is NOT achievable with expression templates.
>
> I can say with certainty that the async/await mechanism is heavily used
> in some codebases and with great benefit. It is being added to all
> languages one after another.
>
> The idea behind macros is that instead of adding new feature to the
> language, the language should propose a toolkit to build these features
> as library.

Agree, good points.

> I don't think the time has come for macros in D. As discussed before, it
> seems like filling the gap in existing feature is more important than
> adding new ones. This should however be considered very seriously when
> the gaps has been filled.

Unfortunately I don't think we will have a feature freeze from now until 
those gaps has been filled. Most likely there will be added a couple of 
small features that could have been solved by AST macros. The problem 
with that is that each of these features, in themselves, are way to 
small to add AST macros for. So instead we get new features and even 
less chance of adding AST macros.

Example. There's a bug report about adding support for C++ namespaces. 
That should be solveable with library code. It's just mangling and we 
already have pragma(mangle).

pragma(mangle, namespace("foo::bar")) extern(C++) void x ();

The problem here is that "x" needs to be mangled as well.

pragma(mangle, namespace("foo::bar", x)) extern(C++) void x ();

The above doesn't work due to forward reference errors.

pragma(mangle, namespace("foo::bar", void function (), "x")) extern(C++) 
void x ();

The problem with the above is that we now need to repeat the signature 
and the name of the function.

With AST macros:

macro namespace (Context context, Ast!(string) name, Declaration 
declaration) { ... }

@namespace("foo::bar") extern (C++) void x ();

This works because the macro receives the whole declaration that is "x" 
and "x" is replaced with whatever the macro returns:

pragma(mangle, "mangled_name_of_x") extern (C++) void x ();

Since it uses the same syntax as UDA's you it can look like real 
namespaces in C++:

@namespace("foo::bar") extern (C++)
{
     void x ();
     void y ();
}

-- 
/Jacob Carlborg


More information about the Digitalmars-d mailing list