-
-
Notifications
You must be signed in to change notification settings - Fork 676
function argument stringification: __traits(getCallerSource, symbol) (variadics work too)
#7821
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
b63ed03
1fc314e
6d6f5fd
842b3ab
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,16 @@ | ||
| Stringify caller's function argument, analog to C's `#` stringification macro (except it's type safe). | ||
|
|
||
| NOTE: it also works with UFCS, with tuples (string static array) and non-tuples (string) | ||
|
|
||
| Eg: | ||
| --- | ||
| string logSimple(T...)(T a, string[T.length] names = __traits(getCallerSource, a)) | ||
| { | ||
| import std.conv; | ||
| return text(names, ": ", a); // see testargnames for a better log function | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Use four spaces for indentation + don't reference to DMD's testsuite in the changelog. |
||
| } | ||
|
|
||
| double x = 1.5; | ||
| logSimple(x * 2, 'a') // ["x * 2", "'a'"]: 3a | ||
| logSimple(__LINE__) // ["__LINE__"]: 9 | ||
| --- | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -309,6 +309,15 @@ extern (C++) final class Module : Package | |
| modules = new DsymbolTable(); | ||
| } | ||
|
|
||
| extern (C++) void releaseResources() | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Global comment: Add Ddoc comment for all new functions. |
||
| { | ||
| // printf("Module::releaseResources %s\n", this.toChars()); | ||
| if (srcfile._ref == 0) | ||
| .free(srcfile.buffer); | ||
| srcfile.buffer = null; | ||
| srcfile.len = 0; | ||
| } | ||
|
|
||
| extern (C++) static __gshared AggregateDeclaration moduleinfo; | ||
|
|
||
| const(char)* arg; // original argument name | ||
|
|
@@ -875,10 +884,12 @@ extern (C++) final class Module : Package | |
| if (p.errors) | ||
| ++global.errors; | ||
| } | ||
| if (srcfile._ref == 0) | ||
| .free(srcfile.buffer); | ||
| srcfile.buffer = null; | ||
| srcfile.len = 0; | ||
|
|
||
| if(global.params.disposeSrcContent) | ||
| { | ||
| releaseResources(); | ||
| } | ||
|
|
||
| /* The symbol table into which the module is to be inserted. | ||
| */ | ||
| DsymbolTable dst; | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -1604,6 +1604,8 @@ extern (C++) abstract class Expression : RootObject | |
| return buf.extractString(); | ||
| } | ||
|
|
||
| // TODO: https://issues.dlang.org/show_bug.cgi?id=18371 Issue 18371 - allow default parameters after `...` (not just template variadics, which are ok now) | ||
| version(all) | ||
| final void error(const(char)* format, ...) const | ||
| { | ||
| if (type != Type.terror) | ||
|
|
@@ -1614,6 +1616,26 @@ extern (C++) abstract class Expression : RootObject | |
| va_end(ap); | ||
| } | ||
| } | ||
| else | ||
| { | ||
| pragma(inline, true) | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. why force inline this? |
||
| extern(D) | ||
| final void error(string file=__FILE__, int line=__LINE__)(const(char)* format, ...) const | ||
| { | ||
| version(with_debug){ | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. where/what is with_debug? |
||
| import std.conv:text; | ||
| writelnL(file, ":", line); | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. where/what is writelnL()? |
||
| } | ||
| if (type != Type.terror) | ||
| { | ||
| va_list ap; | ||
| va_start(ap, format); | ||
| .verror(loc, format, ap); | ||
| va_end(ap); | ||
| } | ||
| } | ||
| } | ||
|
|
||
|
|
||
| final void warning(const(char)* format, ...) const | ||
| { | ||
|
|
@@ -2441,6 +2463,12 @@ extern (C++) abstract class Expression : RootObject | |
| return false; | ||
| } | ||
|
|
||
| // TODO: can we avoid this? | ||
| ArgStringInitExp isArgStringInitExp() | ||
| { | ||
| return null; | ||
| } | ||
|
|
||
| final Expression op_overload(Scope* sc) | ||
| { | ||
| return .op_overload(this, sc); | ||
|
|
@@ -7096,6 +7124,57 @@ extern (C++) final class FileInitExp : DefaultInitExp | |
| } | ||
| } | ||
|
|
||
| /*********************************************************** | ||
| */ | ||
| extern (C++) final class ArgStringInitExp : DefaultInitExp | ||
|
Member
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. What is an ArgStringInitExp? There's no documentation here. |
||
| { | ||
| // function parameter we want stringified | ||
| // NOTE: redundant with exp.args[0],toChars | ||
| Identifier ident; | ||
| TraitsExp exp; | ||
|
|
||
| extern (D) this(const ref Loc loc) | ||
| { | ||
| super(loc, TOK.getCallerSource, __traits(classInstanceSize, ArgStringInitExp)); | ||
| } | ||
|
|
||
| void setIdent(Identifier ident) | ||
| { | ||
| this.ident = ident; | ||
| } | ||
|
|
||
| override ArgStringInitExp isArgStringInitExp() | ||
| { | ||
| return this; | ||
| } | ||
|
|
||
| extern (D) Expression resolveArgString(const ref Loc loc, Scope* sc, string value) | ||
| { | ||
| Expression e = new StringExp(loc, cast(void*)value.ptr, value.length); | ||
| e = e.expressionSemantic(sc); | ||
| e = e.castTo(sc, type); | ||
| return e; | ||
| } | ||
|
|
||
| extern (D) Expression resolveArgStrings(const ref Loc loc, Scope* sc, string[] values) | ||
| { | ||
| auto elements = new Expressions(); | ||
| elements.setDim(values.length); | ||
| foreach(j, value; values){ | ||
| (*elements)[j] = new StringExp(loc, cast(void*)value.ptr, value.length); | ||
| } | ||
| Expression e = new ArrayLiteralExp(loc, elements); | ||
| e = e.expressionSemantic(sc); | ||
| e = e.castTo(sc, type); | ||
| return e; | ||
| } | ||
|
|
||
| override void accept(Visitor v) | ||
| { | ||
| v.visit(this); | ||
| } | ||
| } | ||
|
|
||
| /*********************************************************** | ||
| */ | ||
| extern (C++) final class LineInitExp : DefaultInitExp | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What exactly are you adding?
__traits(getCallerSource, a)? Or is it more than that?