Providing #version from the main program suggested by PeterT in the above comment is the only way that will work. The ability to do this (and the ability to define constants without having anything like the one available for the -D compiler) is the main intention of glShaderSource to take an array of pointers, not a simple char* .
The GLSL specification (chapter 3.3) requires that #version be the first in the shader source, with the exception of spaces and comments.
So a thing like
#ifdef foo #version 123 #endif
is valid and no such thing will compile (unless the shader compiler is overly permissive, i.e. broken).
On your second question, conditional compilation certainly works and uses it the way you intend to do, which is good.
Damon source share