Thread overview
Debugging by old fashioned trace log printfs / writefln
Jun 29, 2023
Cecil Ward
Jun 29, 2023
Chris Katko
Jun 30, 2023
Cecil Ward
Jun 30, 2023
H. S. Teoh
Jun 30, 2023
Jonathan M Davis
June 29, 2023
I’m trying to debug my D program with old-fashioned printfs stuck in various strategic places, actually using writefln(). My problem is that the addition of printf fights with the existing declarations for pure nothrow @nogc @safe and I have to adjust them, then put them back correctly when the writefln() trace statements are later removed.

Is there something else I could be using, something that is allowed to violate the checking rules for purity, nothrow, @nogc? Would pragma( msg, "…" ) do the trick? Is that what I should be using?
June 30, 2023
```d
debug {
	writeln("text");
}
```

```d
writeln(__MODULE__, ":", __LINE__, " ", "stuff");
```

You'll need to wrap try/catch for flushing stdout however.
June 30, 2023
```d
debug writeln(__MODULE__, ":", __LINE__, " ", "stuff");
```
Opps missed the debug.
June 29, 2023

On Thursday, 29 June 2023 at 18:27:22 UTC, Cecil Ward wrote:

>

I’m trying to debug my D program with old-fashioned printfs stuck in various strategic places, actually using writefln(). My problem is that the addition of printf fights with the existing declarations for pure nothrow @nogc @safe and I have to adjust them, then put them back correctly when the writefln() trace statements are later removed.

Is there something else I could be using, something that is allowed to violate the checking rules for purity, nothrow, @nogc? Would pragma( msg, "…" ) do the trick? Is that what I should be using?

pragma(msg, "") is only for compile time. It for debugging functions/templates if they're actually used (which static path is used), instantiated, and you can also get type values from template inputs to confirm they're what you expect. "Oh this is a char[][] not a char[]!"

pragmas are the D equivalent of C/C++ pragmas. In this case, C/C++:

#pragma message( message-string )
June 30, 2023
On Thursday, 29 June 2023 at 23:54:45 UTC, Chris Katko wrote:
> On Thursday, 29 June 2023 at 18:27:22 UTC, Cecil Ward wrote:
>> I’m trying to debug my D program with old-fashioned printfs stuck in various strategic places, actually using writefln(). My problem is that the addition of printf fights with the existing declarations for pure nothrow @nogc @safe and I have to adjust them, then put them back correctly when the writefln() trace statements are later removed.
>>
>> Is there something else I could be using, something that is allowed to violate the checking rules for purity, nothrow, @nogc? Would pragma( msg, "…" ) do the trick? Is that what I should be using?
>
> pragma(msg, "") is only for compile time. It for debugging functions/templates if they're actually used (which static path is used), instantiated, and you can also get type values from template inputs to confirm they're what you expect. "Oh this is a char[][] not a char[]!"
>
> pragmas are the D equivalent of C/C++ pragmas. In this case, C/C++:
> ```C
> #pragma message( message-string )
> ```

Since I can pass my main function some compile-time-defined input, the whole program should be capable of being executed with CTFE, no? So in that case pragma( msg ) should suffice for a test situation? Would pragma(message) have the advantage over writefln that I don’t have to pervert the function attributes like nogc nothrow pure ?
June 30, 2023
On Fri, Jun 30, 2023 at 03:43:14PM +0000, Cecil Ward via Digitalmars-d-learn wrote: [...]
> Since I can pass my main function some compile-time-defined input, the whole program should be capable of being executed with CTFE, no? So in that case pragma( msg ) should suffice for a test situation? Would pragma(message) have the advantage over writefln that I don’t have to pervert the function attributes like nogc nothrow pure ?

Just use the `debug` statement:

	auto pureFunc(Args args) pure {
		...
		debug writefln("debug info: %s", ...);
		...
	}

Compile with `-debug` to enable the writefln during development. When not compiling with `-debug`, the writefln will not be compiled and the function will actually be pure.

The problem with pragma(msg) is that it happens very early in the compilation process; some things may not be available to it, such as the value of variables in CTFE. This may limit its usefulness in some situations.  For more details on this, see:

	https://wiki.dlang.org/Compile-time_vs._compile-time


T

-- 
He who sacrifices functionality for ease of use, loses both and deserves neither. -- Slashdotter
June 30, 2023
On Thursday, June 29, 2023 12:27:22 PM MDT Cecil Ward via Digitalmars-d-learn wrote:
> I’m trying to debug my D program with old-fashioned printfs stuck
> in various strategic places, actually using writefln(). My
> problem is that the addition of printf fights with the existing
> declarations for pure nothrow @nogc @safe and I have to adjust
> them, then put them back correctly when the writefln() trace
> statements are later removed.
>
> Is there something else I could be using, something that is allowed to violate the checking rules for purity, nothrow, @nogc? Would pragma( msg, "…" ) do the trick? Is that what I should be using?

pragma(msg, ...) and writeln are fundamentally different.

pragmas are run when code is compiled. When you calling a function during CTFE, you are calling that function. You are not compiling it. It has already been compiled at that point. That function may be being called as part of compiling another function, but function that you're calling has already been compiled. So, something like

string foo() { return "foo"; }

void bar(int i)
{
    pragma(msg, foo());
}

will compile just fine, and it will print out "foo" at compile time, whereas

void bar(int i)
{
    pragma(msg, i);
}

will not compile.

void bar(int i)
{
    writeln(i);
}

will compile, but it won't print anything when it's compiled, and it cannot be called with CTFE. However, it will of course print out if called at runtime.

If you need to print out a message during testing, and the function in question has attributes that writeln does not satisfy, then you can use debug statements and compile the code with the -debug flag.

https://dlang.org/spec/version.html#debug

e.g.

void foo() pure @safe
{
    debug
    {
        writeln("hello");
    }
}

Of course, you have to be very careful when you do that, since you'll get undefined behavior if the debug statements have side effects which violate the guarantees that those attributes are supposed to make (e.g. mutating a global variable in a pure function or throwing an exception from a nothrow function), but simply printing out stuff shouldn't be a problem unless generating the strings to print has side effects.

- Jonathan M Davis