18 const char* kFunctionEmulationVertexSource[] = {
19 "#error no emulation for cos(float)",
20 "#error no emulation for cos(vec2)",
21 "#error no emulation for cos(vec3)",
22 "#error no emulation for cos(vec4)",
24 "#define webgl_distance_emu(x, y) ((x) >= (y) ? (x) - (y) : (y) - (x))",
25 "#error no emulation for distance(vec2, vec2)",
26 "#error no emulation for distance(vec3, vec3)",
27 "#error no emulation for distance(vec4, vec4)",
29 "#define webgl_dot_emu(x, y) ((x) * (y))",
30 "#error no emulation for dot(vec2, vec2)",
31 "#error no emulation for dot(vec3, vec3)",
32 "#error no emulation for dot(vec4, vec4)",
34 "#define webgl_length_emu(x) ((x) >= 0.0 ? (x) : -(x))",
35 "#error no emulation for length(vec2)",
36 "#error no emulation for length(vec3)",
37 "#error no emulation for length(vec4)",
39 "#define webgl_normalize_emu(x) ((x) == 0.0 ? 0.0 : ((x) > 0.0 ? 1.0 : -1.0))",
40 "#error no emulation for normalize(vec2)",
41 "#error no emulation for normalize(vec3)",
42 "#error no emulation for normalize(vec4)",
44 "#define webgl_reflect_emu(I, N) ((I) - 2.0 * (N) * (I) * (N))",
45 "#error no emulation for reflect(vec2, vec2)",
46 "#error no emulation for reflect(vec3, vec3)",
47 "#error no emulation for reflect(vec4, vec4)"
50 const char* kFunctionEmulationFragmentSource[] = {
51 "webgl_emu_precision float webgl_cos_emu(webgl_emu_precision float a) { return cos(a); }",
52 "webgl_emu_precision vec2 webgl_cos_emu(webgl_emu_precision vec2 a) { return cos(a); }",
53 "webgl_emu_precision vec3 webgl_cos_emu(webgl_emu_precision vec3 a) { return cos(a); }",
54 "webgl_emu_precision vec4 webgl_cos_emu(webgl_emu_precision vec4 a) { return cos(a); }",
56 "#define webgl_distance_emu(x, y) ((x) >= (y) ? (x) - (y) : (y) - (x))",
57 "#error no emulation for distance(vec2, vec2)",
58 "#error no emulation for distance(vec3, vec3)",
59 "#error no emulation for distance(vec4, vec4)",
61 "#define webgl_dot_emu(x, y) ((x) * (y))",
62 "#error no emulation for dot(vec2, vec2)",
63 "#error no emulation for dot(vec3, vec3)",
64 "#error no emulation for dot(vec4, vec4)",
66 "#define webgl_length_emu(x) ((x) >= 0.0 ? (x) : -(x))",
67 "#error no emulation for length(vec2)",
68 "#error no emulation for length(vec3)",
69 "#error no emulation for length(vec4)",
71 "#define webgl_normalize_emu(x) ((x) == 0.0 ? 0.0 : ((x) > 0.0 ? 1.0 : -1.0))",
72 "#error no emulation for normalize(vec2)",
73 "#error no emulation for normalize(vec3)",
74 "#error no emulation for normalize(vec4)",
76 "#define webgl_reflect_emu(I, N) ((I) - 2.0 * (N) * (I) * (N))",
77 "#error no emulation for reflect(vec2, vec2)",
78 "#error no emulation for reflect(vec3, vec3)",
79 "#error no emulation for reflect(vec4, vec4)"
82 const bool kFunctionEmulationVertexMask[] = {
83 #if defined(__APPLE__)
139 const bool kFunctionEmulationFragmentMask[] = {
140 #if defined(__APPLE__)
199 : mEmulator(emulator)
206 bool needToEmulate = mEmulator.SetFunctionCalled(
219 switch (node->
getOp()) {
248 if (sequence.size() != 2)
252 if (!param1 || !param2)
254 bool needToEmulate = mEmulator.SetFunctionCalled(
271 mFunctionMask = kFunctionEmulationFragmentMask;
272 mFunctionSource = kFunctionEmulationFragmentSource;
274 mFunctionMask = kFunctionEmulationVertexMask;
275 mFunctionSource = kFunctionEmulationVertexSource;
282 TBuiltInFunction
function = IdentifyFunction(op, param);
289 TBuiltInFunction
function = IdentifyFunction(op, param1, param2);
294 BuiltInFunctionEmulator::TBuiltInFunction
function) {
295 if (
function == TFunctionUnknown || mFunctionMask[
function] ==
false)
297 for (
size_t i = 0;
i < mFunctions.size(); ++
i) {
298 if (mFunctions[
i] ==
function)
301 mFunctions.push_back(
function);
308 if (mFunctions.size() == 0)
310 out <<
"// BEGIN: Generated code for built-in function emulation\n\n";
312 out <<
"#if defined(GL_FRAGMENT_PRECISION_HIGH)\n"
313 <<
"#define webgl_emu_precision highp\n"
315 <<
"#define webgl_emu_precision mediump\n"
318 out <<
"#define webgl_emu_precision\n\n";
320 for (
size_t i = 0;
i < mFunctions.size(); ++
i) {
321 out << mFunctionSource[mFunctions[
i]] <<
"\n\n";
323 out <<
"// END: Generated code for built-in function emulation\n\n";
326 BuiltInFunctionEmulator::TBuiltInFunction
327 BuiltInFunctionEmulator::IdentifyFunction(
331 return TFunctionUnknown;
332 unsigned int function = TFunctionUnknown;
335 function = TFunctionCos1;
338 function = TFunctionLength1;
341 function = TFunctionNormalize1;
346 if (
function == TFunctionUnknown)
347 return TFunctionUnknown;
350 return static_cast<TBuiltInFunction
>(
function);
353 BuiltInFunctionEmulator::TBuiltInFunction
354 BuiltInFunctionEmulator::IdentifyFunction(
362 return TFunctionUnknown;
364 unsigned int function = TFunctionUnknown;
367 function = TFunctionDistance1_1;
370 function = TFunctionDot1_1;
373 function = TFunctionReflect1_1;
378 if (
function == TFunctionUnknown)
379 return TFunctionUnknown;
382 return static_cast<TBuiltInFunction
>(
function);
390 BuiltInFunctionEmulationMarker
marker(*
this);
403 ASSERT(name[name.length() - 1] ==
'(');
404 return "webgl_" + name.substr(0, name.length() - 1) +
"_emu(";
TIntermSequence & getSequence()
int getNominalSize() const
EGLImageKHR EGLint * name
bool SetFunctionCalled(TOperator op, const TType ¶m)
void setUseEmulatedFunction()
static TString GetEmulatedFunctionName(const TString &name)
#define ASSERT(expression)
virtual void traverse(TIntermTraverser *)=0
const TType & getType() const
TIntermTyped * getOperand()
std::basic_string< char, std::char_traits< char >, TStringAllocator > TString
BuiltInFunctionEmulator(ShShaderType shaderType)
void setUseEmulatedFunction()
void MarkBuiltInFunctionsForEmulation(TIntermNode *root)
void OutputEmulatedFunctionDefinition(TInfoSinkBase &out, bool withPrecision) const