On Thursday, 18 February 2016 at 07:21:05 UTC, Chris Katko wrote:
Hello. I'm almost brand-new to the D language and still absorbing things.

I'm wondering if it's possible to fire off a compile-time (or worst case, a run-time) warning or error if a function is called, but the return value is not checked.

I'm not trying to enforce whether someone actually deciphers the value's meaning correctly. I just want to enforce that somewhere, a variable or expression is receiving the return value of a particular function.

Any ideas?

I imagine I could use a compiler flag to warn, but that's a global setting. I'm looking more for a specified subset of functions.

Off hand, I see two reasonable ways to do this:

1) Instead of actually returning the value, require the caller to pass the destination variable as a `ref` or `out` parameter.

Disadvantages: This could be a bit slower than using actual return values, and it would change the syntax.

2) Wrap the return value in a struct like this:

struct MustUse(T) {
pure: nothrow:

private:
    T payload;
    bool used;

public:
    @property ref T use() @nogc {
        used = true;
        return payload;
    }
    alias use this;

    this(T payload) @nogc {
        this.payload = payload;
        this.used = false;
    }   
    ~this() {
        if(!used)
throw new Error(T.stringof ~ " return value was not used.");
    }

}

// For convenience, use this function to infer T from the type of paylaod.
MustUse!T mustUse(T)(T payload) {
    return MustUse!T(payload); }

Example on DPaste: http://dpaste.dzfl.pl/8ba6ebf05f32

With inlining and optimizations, even the above generic implementation might be faster than passing by ref/out. A specialization for non-null pointer values could almost certainly be faster.

Disadvantages: On the other hand, it might be slower. The only way to know for sure, is to write some non-trivial examples and benchmark. Regardless, the fact that it signals the error at runtime instead of compile time could be annoying.

Reply via email to