So why doesn't popFront return an element?

bearophile bearophileHUGS at lycos.com
Wed Apr 13 17:39:28 PDT 2011


Andrej Mitrovic:

> Oh, I thought the compiler could optimize calls to popFront if I'm not
> assigning its value.
> 
> Doesn't a technique exist where if a function is called and I'm not
> assigning its result anywhere it should simply exit the function
> without returning anything? It seems like a valuable compiler
> optimization, if that is even possible.

The function may have different calling points, including having its pointer taken and passed around. So you generally need the full compiled function, that generates the output too.

If the compiler is able to perform some kind of "whole program optimization" (today both GCC and LLVM are able to do some of it), and the compiler is able to infer that the result of popFront is never used in the whole program, then it might be able to remove the dead code that generates the output.

If the compiler inlines popFront at a call point, and in this call point the result is not used, all compilers are usually able to remove the useless computations of the result.

Some time ago I have proposed a __used_result boolean flag, usable inside functions. If inside a function you use this value (inside a "static if"), the function becomes a template, and it generally gets compiled two times in the final binary. If at a calling point the result of the function doesn't get used, the compiler calls the template instantiation where __used_result is false, so with the static if you are able to avoid computing the result.

So this program:

int count = 0;

int foo(int x) {
    count++;
    static if (__used_result) {
        int result = x * x;
        return result;
    }
}

void main() {
	foo(10);
	int y = foo(20);
}


Gets rewritten by the compiler to something like:

int count = 0;

auto foo(bool use_return)(int x) {
    count++;
    static if (use_return) {
        int result = x * x;
        return result;
    }
}

void main() {
    foo!false(10);
    int y = foo!true(20);
}


That produces:

_D4test11__T3fooVb0Z3fooFiZv	comdat
		push	EAX
		mov	ECX,FS:__tls_array
		mov	EDX,[ECX]
		inc	dword ptr _D4test5counti[EDX]
		pop	EAX
		ret

_D4test11__T3fooVb1Z3fooFiZi	comdat
		push	EAX
		mov	ECX,FS:__tls_array
		mov	EDX,[ECX]
		inc	dword ptr _D4test5counti[EDX]
		imul	EAX,EAX
		pop	ECX
		ret

Bye,
bearophile


More information about the Digitalmars-d-learn mailing list