mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Bug 690735 - upgrade ANGLE to r774 - no review, just syncing with upstream
This doesn't involve any Makefile change so should be relatively safe. This is needed for: * BUILTIN_FUNCTION_EMULATION (r773,774), blocker for 665578 * extensions validation in shaders (r745), blocker for 684853 * major performance improvements and bug fixes
This commit is contained in:
parent
10cd4a93c8
commit
d0562bfee9
@ -1,15 +1,16 @@
|
||||
This is the ANGLE project, from http://code.google.com/p/angleproject/.
|
||||
This is the ANGLE project, from http://code.google.com/p/angleproject/
|
||||
|
||||
Current revision: r740
|
||||
Current revision: r774
|
||||
|
||||
== Applied local patches ==
|
||||
|
||||
In this order:
|
||||
angle-nspr-misc.patch - don't bother with ANGLE_OS detection with NSPR
|
||||
angle-renaming.patch - rename debug.h to compilerdebug.h to avoid conflict in our makefiles
|
||||
angle-intrinsic-msvc2005.patch - work around a MSVC 2005 compile error
|
||||
angle-instrinsic-msvc2005.patch - work around a MSVC 2005 compile error
|
||||
angle-limit-identifiers-to-250-chars.patch - see bug 675625
|
||||
angle-use-xmalloc.patch - see bug 680840. Can drop this patch whenever the new preprocessor lands.
|
||||
angle-mCurrentValueOffsets-size_t.patch - ANGLE bug 220 - compile fix on win64
|
||||
|
||||
In addition to these patches, the Makefile.in files are ours, they're not present in upsteam ANGLE.
|
||||
|
||||
|
@ -1,5 +1,39 @@
|
||||
# HG changeset patch
|
||||
# Parent 09fc6e32e6c5d4cdcb3c01f6849ccb8cdae7e8e0
|
||||
# Parent cf38970fcf3b4bee12f09b3747b7b7711bc77ad8
|
||||
diff --git a/gfx/angle/angle-renaming-debug.patch b/gfx/angle/angle-renaming-debug.patch
|
||||
--- a/gfx/angle/angle-renaming-debug.patch
|
||||
+++ b/gfx/angle/angle-renaming-debug.patch
|
||||
@@ -1,11 +1,10 @@
|
||||
# HG changeset patch
|
||||
-# Parent 96359f46b01fdb37e791f564495e8b2755a05233
|
||||
-
|
||||
+# Parent 70640278da97b0ca49e21c4bb52766b8af7db4db
|
||||
diff --git a/gfx/angle/Makefile.in b/gfx/angle/Makefile.in
|
||||
--- a/gfx/angle/Makefile.in
|
||||
+++ b/gfx/angle/Makefile.in
|
||||
@@ -73,17 +73,17 @@ CPPSRCS = \
|
||||
parseConst.cpp \
|
||||
ParseHelper.cpp \
|
||||
PoolAlloc.cpp \
|
||||
QualifierAlive.cpp \
|
||||
@@ -129,17 +128,17 @@ diff --git a/gfx/angle/src/compiler/comp
|
||||
|
||||
#include <assert.h>
|
||||
|
||||
#ifdef _DEBUG
|
||||
#define TRACE_ENABLED // define to enable debug message tracing
|
||||
diff --git a/gfx/angle/src/compiler/osinclude.h b/gfx/angle/src/compiler/osinclude.h
|
||||
--- a/gfx/angle/src/compiler/osinclude.h
|
||||
+++ b/gfx/angle/src/compiler/osinclude.h
|
||||
-@@ -32,17 +32,17 @@
|
||||
+@@ -30,17 +30,17 @@
|
||||
#include <windows.h>
|
||||
#elif defined(ANGLE_OS_POSIX)
|
||||
#include <pthread.h>
|
||||
#include <semaphore.h>
|
||||
#include <errno.h>
|
||||
#endif // ANGLE_USE_NSPR
|
||||
|
||||
|
||||
diff --git a/gfx/angle/src/libGLESv2/Texture.cpp b/gfx/angle/src/libGLESv2/Texture.cpp
|
||||
--- a/gfx/angle/src/libGLESv2/Texture.cpp
|
||||
|
@ -1,3 +1,5 @@
|
||||
# HG changeset patch
|
||||
# Parent f9415c10c3ebd27856500cca7a0ee0f28a16f53c
|
||||
diff --git a/gfx/angle/src/compiler/preprocessor/scanner.h b/gfx/angle/src/compiler/preprocessor/scanner.h
|
||||
--- a/gfx/angle/src/compiler/preprocessor/scanner.h
|
||||
+++ b/gfx/angle/src/compiler/preprocessor/scanner.h
|
||||
|
24
gfx/angle/angle-mCurrentValueOffsets-size_t.patch
Normal file
24
gfx/angle/angle-mCurrentValueOffsets-size_t.patch
Normal file
@ -0,0 +1,24 @@
|
||||
# HG changeset patch
|
||||
# Parent 693fb23429fdbf40e272e1c48887479cc597e0bc
|
||||
diff --git a/gfx/angle/src/libGLESv2/VertexDataManager.h b/gfx/angle/src/libGLESv2/VertexDataManager.h
|
||||
--- a/gfx/angle/src/libGLESv2/VertexDataManager.h
|
||||
+++ b/gfx/angle/src/libGLESv2/VertexDataManager.h
|
||||
@@ -127,17 +127,17 @@ class VertexDataManager
|
||||
|
||||
Context *const mContext;
|
||||
IDirect3DDevice9 *const mDevice;
|
||||
|
||||
StreamingVertexBuffer *mStreamingBuffer;
|
||||
|
||||
bool mDirtyCurrentValue[MAX_VERTEX_ATTRIBS];
|
||||
StreamingVertexBuffer *mCurrentValueBuffer[MAX_VERTEX_ATTRIBS];
|
||||
- UINT mCurrentValueOffsets[MAX_VERTEX_ATTRIBS];
|
||||
+ std::size_t mCurrentValueOffsets[MAX_VERTEX_ATTRIBS];
|
||||
|
||||
// Attribute format conversion
|
||||
struct FormatConverter
|
||||
{
|
||||
bool identity;
|
||||
std::size_t outputElementSize;
|
||||
void (*convertArray)(const void *in, std::size_t stride, std::size_t n, void *out);
|
||||
D3DDECLTYPE d3dDeclType;
|
@ -1,26 +1,2 @@
|
||||
# HG changeset patch
|
||||
# Parent 99de3c7d00973e65e295911b2b8b66c75cfe24bb
|
||||
diff --git a/gfx/angle/src/compiler/osinclude.h b/gfx/angle/src/compiler/osinclude.h
|
||||
--- a/gfx/angle/src/compiler/osinclude.h
|
||||
+++ b/gfx/angle/src/compiler/osinclude.h
|
||||
@@ -7,17 +7,19 @@
|
||||
#ifndef __OSINCLUDE_H
|
||||
#define __OSINCLUDE_H
|
||||
|
||||
//
|
||||
// This file contains contains os-specific datatypes and
|
||||
// declares any os-specific functions.
|
||||
//
|
||||
|
||||
-#if defined(_WIN32) || defined(_WIN64)
|
||||
+#if defined(ANGLE_USE_NSPR)
|
||||
+/* no need to define anything when using NSPR */
|
||||
+#elif defined(_WIN32) || defined(_WIN64)
|
||||
#define ANGLE_OS_WIN
|
||||
#elif defined(__APPLE__) || defined(__linux__) || \
|
||||
defined(__FreeBSD__) || defined(__OpenBSD__) || \
|
||||
defined(__sun)
|
||||
#define ANGLE_OS_POSIX
|
||||
#else
|
||||
#error Unsupported platform.
|
||||
#endif
|
||||
# Parent 6a9ec71ad85de76c551a5398b1427d9f76430b1f
|
||||
|
@ -1,6 +1,5 @@
|
||||
# HG changeset patch
|
||||
# Parent 96359f46b01fdb37e791f564495e8b2755a05233
|
||||
|
||||
# Parent 70640278da97b0ca49e21c4bb52766b8af7db4db
|
||||
diff --git a/gfx/angle/Makefile.in b/gfx/angle/Makefile.in
|
||||
--- a/gfx/angle/Makefile.in
|
||||
+++ b/gfx/angle/Makefile.in
|
||||
@ -134,7 +133,7 @@ diff --git a/gfx/angle/src/compiler/compilerdebug.h b/gfx/angle/src/compiler/com
|
||||
diff --git a/gfx/angle/src/compiler/osinclude.h b/gfx/angle/src/compiler/osinclude.h
|
||||
--- a/gfx/angle/src/compiler/osinclude.h
|
||||
+++ b/gfx/angle/src/compiler/osinclude.h
|
||||
@@ -32,17 +32,17 @@
|
||||
@@ -30,17 +30,17 @@
|
||||
#include <windows.h>
|
||||
#elif defined(ANGLE_OS_POSIX)
|
||||
#include <pthread.h>
|
||||
|
145
gfx/angle/angle-use-xmalloc.patch
Normal file
145
gfx/angle/angle-use-xmalloc.patch
Normal file
@ -0,0 +1,145 @@
|
||||
# HG changeset patch
|
||||
# Parent 74f1894d664435118be4fdefd53cabfdaa9985bc
|
||||
diff --git a/gfx/angle/Makefile.in b/gfx/angle/Makefile.in
|
||||
--- a/gfx/angle/Makefile.in
|
||||
+++ b/gfx/angle/Makefile.in
|
||||
@@ -123,16 +123,18 @@ CSRCS = \
|
||||
memory.c \
|
||||
scanner.c \
|
||||
symbols.c \
|
||||
tokens.c \
|
||||
$(NULL)
|
||||
|
||||
DEFINES += -DANGLE_USE_NSPR -DANGLE_BUILD
|
||||
|
||||
+EXTRA_DSO_LDOPTS = $(MOZALLOC_LIB)
|
||||
+
|
||||
ifdef MOZ_ANGLE
|
||||
|
||||
# libEGL depends on (links against!) libGLESv2!
|
||||
DIRS = src/libGLESv2 src/libEGL
|
||||
|
||||
libs::
|
||||
expand "$(MOZ_D3DX9_CAB)" -F:$(MOZ_D3DX9_DLL) "$(DIST)/bin"
|
||||
expand "$(MOZ_D3DCOMPILER_CAB)" -F:$(MOZ_D3DCOMPILER_DLL) "$(DIST)/bin"
|
||||
diff --git a/gfx/angle/README.mozilla b/gfx/angle/README.mozilla
|
||||
--- a/gfx/angle/README.mozilla
|
||||
+++ b/gfx/angle/README.mozilla
|
||||
@@ -4,16 +4,17 @@ Current revision: r740
|
||||
|
||||
== Applied local patches ==
|
||||
|
||||
In this order:
|
||||
angle-nspr-misc.patch - don't bother with ANGLE_OS detection with NSPR
|
||||
angle-renaming.patch - rename debug.h to compilerdebug.h to avoid conflict in our makefiles
|
||||
angle-intrinsic-msvc2005.patch - work around a MSVC 2005 compile error
|
||||
angle-limit-identifiers-to-250-chars.patch - see bug 675625
|
||||
+ angle-use-xmalloc.patch - see bug 680840. Can drop this patch whenever the new preprocessor lands.
|
||||
|
||||
In addition to these patches, the Makefile.in files are ours, they're not present in upsteam ANGLE.
|
||||
|
||||
== How to update this ANGLE copy ==
|
||||
|
||||
1. Unapply patches
|
||||
2. Apply diff with new ANGLE version
|
||||
3. Reapply patches.
|
||||
diff --git a/gfx/angle/angle-limit-identifiers-to-250-chars.patch b/gfx/angle/angle-limit-identifiers-to-250-chars.patch
|
||||
--- a/gfx/angle/angle-limit-identifiers-to-250-chars.patch
|
||||
+++ b/gfx/angle/angle-limit-identifiers-to-250-chars.patch
|
||||
@@ -1,8 +1,10 @@
|
||||
+# HG changeset patch
|
||||
+# Parent f9415c10c3ebd27856500cca7a0ee0f28a16f53c
|
||||
diff --git a/gfx/angle/src/compiler/preprocessor/scanner.h b/gfx/angle/src/compiler/preprocessor/scanner.h
|
||||
--- a/gfx/angle/src/compiler/preprocessor/scanner.h
|
||||
+++ b/gfx/angle/src/compiler/preprocessor/scanner.h
|
||||
@@ -44,17 +44,19 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILI
|
||||
//
|
||||
// scanner.h
|
||||
//
|
||||
|
||||
diff --git a/gfx/angle/src/compiler/preprocessor/atom.c b/gfx/angle/src/compiler/preprocessor/atom.c
|
||||
--- a/gfx/angle/src/compiler/preprocessor/atom.c
|
||||
+++ b/gfx/angle/src/compiler/preprocessor/atom.c
|
||||
@@ -48,16 +48,18 @@ NVIDIA HAS BEEN ADVISED OF THE POSSIBILI
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "compiler/compilerdebug.h"
|
||||
#include "compiler/preprocessor/slglobals.h"
|
||||
|
||||
+#include "../../../../../memory/mozalloc/mozalloc.h"
|
||||
+
|
||||
#undef malloc
|
||||
#undef realloc
|
||||
#undef free
|
||||
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////
|
||||
////////////////////////////////////////// String table: //////////////////////////////////////
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
@@ -318,31 +320,23 @@ static int AddAtomFixed(AtomTable *atabl
|
||||
*/
|
||||
|
||||
static int GrowAtomTable(AtomTable *atable, int size)
|
||||
{
|
||||
int *newmap, *newrev;
|
||||
|
||||
if (atable->size < size) {
|
||||
if (atable->amap) {
|
||||
- newmap = realloc(atable->amap, sizeof(int)*size);
|
||||
- newrev = realloc(atable->arev, sizeof(int)*size);
|
||||
+ newmap = moz_xrealloc(atable->amap, sizeof(int)*size);
|
||||
+ newrev = moz_xrealloc(atable->arev, sizeof(int)*size);
|
||||
} else {
|
||||
- newmap = malloc(sizeof(int)*size);
|
||||
- newrev = malloc(sizeof(int)*size);
|
||||
+ newmap = moz_xmalloc(sizeof(int)*size);
|
||||
+ newrev = moz_xmalloc(sizeof(int)*size);
|
||||
atable->size = 0;
|
||||
}
|
||||
- if (!newmap || !newrev) {
|
||||
- /* failed to grow -- error */
|
||||
- if (newmap)
|
||||
- atable->amap = newmap;
|
||||
- if (newrev)
|
||||
- atable->arev = newrev;
|
||||
- return -1;
|
||||
- }
|
||||
memset(&newmap[atable->size], 0, (size - atable->size) * sizeof(int));
|
||||
memset(&newrev[atable->size], 0, (size - atable->size) * sizeof(int));
|
||||
atable->amap = newmap;
|
||||
atable->arev = newrev;
|
||||
atable->size = size;
|
||||
}
|
||||
return 0;
|
||||
} // GrowAtomTable
|
||||
diff --git a/gfx/angle/src/libEGL/Makefile.in b/gfx/angle/src/libEGL/Makefile.in
|
||||
--- a/gfx/angle/src/libEGL/Makefile.in
|
||||
+++ b/gfx/angle/src/libEGL/Makefile.in
|
||||
@@ -150,8 +150,10 @@ RCFILE = $(srcdir)/libEGL.rc
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
EXTRA_DSO_LDOPTS = "$(MOZ_DIRECTX_SDK_PATH)/lib/$(MOZ_DIRECTX_SDK_CPU_SUFFIX)/d3d9.lib" \
|
||||
"$(MOZ_DIRECTX_SDK_PATH)/lib/$(MOZ_DIRECTX_SDK_CPU_SUFFIX)/dxguid.lib" \
|
||||
"$(DIST)/lib/libGLESv2.lib" \
|
||||
dwmapi.lib \
|
||||
delayimp.lib \
|
||||
/delayload:dwmapi.dll
|
||||
+
|
||||
+EXTRA_DSO_LDOPTS += $(MOZALLOC_LIB)
|
||||
diff --git a/gfx/angle/src/libGLESv2/Makefile.in b/gfx/angle/src/libGLESv2/Makefile.in
|
||||
--- a/gfx/angle/src/libGLESv2/Makefile.in
|
||||
+++ b/gfx/angle/src/libGLESv2/Makefile.in
|
||||
@@ -159,8 +159,10 @@ CPPSRCS += \
|
||||
DEFFILE = $(srcdir)/libGLESv2.def
|
||||
RCFILE = $(srcdir)/libGLESv2.rc
|
||||
|
||||
include $(topsrcdir)/config/rules.mk
|
||||
|
||||
EXTRA_DSO_LDOPTS = "$(MOZ_DIRECTX_SDK_PATH)/lib/$(MOZ_DIRECTX_SDK_CPU_SUFFIX)/d3d9.lib" \
|
||||
"$(MOZ_DIRECTX_SDK_PATH)/lib/$(MOZ_DIRECTX_SDK_CPU_SUFFIX)/d3dx9.lib" \
|
||||
"$(MOZ_DIRECTX_SDK_PATH)/lib/$(MOZ_DIRECTX_SDK_CPU_SUFFIX)/D3DCompiler.lib"
|
||||
+
|
||||
+EXTRA_DSO_LDOPTS += $(MOZALLOC_LIB)
|
@ -97,7 +97,17 @@ int main(int argc, char* argv[])
|
||||
failCode = EFailUsage;
|
||||
}
|
||||
break;
|
||||
case 'a': resources.OES_EGL_image_external = 1; break;
|
||||
case 'x':
|
||||
if (argv[0][2] == '=') {
|
||||
switch (argv[0][3]) {
|
||||
case 'i': resources.OES_EGL_image_external = 1; break;
|
||||
case 'd': resources.OES_standard_derivatives = 1; break;
|
||||
default: failCode = EFailUsage;
|
||||
}
|
||||
} else {
|
||||
failCode = EFailUsage;
|
||||
}
|
||||
break;
|
||||
default: failCode = EFailUsage;
|
||||
}
|
||||
} else {
|
||||
@ -178,7 +188,7 @@ int main(int argc, char* argv[])
|
||||
//
|
||||
void usage()
|
||||
{
|
||||
printf("Usage: translate [-i -m -o -u -l -e -b=e -b=g -b=h -a] file1 file2 ...\n"
|
||||
printf("Usage: translate [-i -m -o -u -l -e -b=e -b=g -b=h -x=i -x=d] file1 file2 ...\n"
|
||||
"Where: filename : filename ending in .frag or .vert\n"
|
||||
" -i : print intermediate tree\n"
|
||||
" -m : map long variable names\n"
|
||||
@ -189,7 +199,8 @@ void usage()
|
||||
" -b=e : output GLSL ES code (this is by default)\n"
|
||||
" -b=g : output GLSL code\n"
|
||||
" -b=h : output HLSL code\n"
|
||||
" -a : enable GL_OES_EGL_image_external\n");
|
||||
" -x=i : enable GL_OES_EGL_image_external\n"
|
||||
" -x=d : enable GL_OES_EGL_standard_derivatives\n");
|
||||
}
|
||||
|
||||
//
|
||||
|
@ -1,7 +1,7 @@
|
||||
#define MAJOR_VERSION 0
|
||||
#define MINOR_VERSION 0
|
||||
#define BUILD_VERSION 0
|
||||
#define BUILD_REVISION 740
|
||||
#define BUILD_REVISION 774
|
||||
|
||||
#define STRINGIFY(x) #x
|
||||
#define MACRO_STRINGIFY(x) STRINGIFY(x)
|
||||
|
@ -10,19 +10,210 @@
|
||||
|
||||
namespace {
|
||||
|
||||
const char* kFunctionEmulationSource[] = {
|
||||
"float webgl_normalize_emu(float a) { return normalize(a) * 1; }",
|
||||
"vec2 webgl_normalize_emu(vec2 a) { return normalize(a) * 1; }",
|
||||
"vec3 webgl_normalize_emu(vec3 a) { return normalize(a) * 1; }",
|
||||
"vec4 webgl_normalize_emu(vec4 a) { return normalize(a) * 1; }",
|
||||
"float webgl_abs_emu(float a) { float rt = abs(a); if (rt < 0.0) rt = 0.0; return rt; }",
|
||||
"vec2 webgl_abs_emu(vec2 a) { vec2 rt = abs(a); if (rt[0] < 0.0) rt[0] = 0.0; return rt; }",
|
||||
"vec3 webgl_abs_emu(vec3 a) { vec3 rt = abs(a); if (rt[0] < 0.0) rt[0] = 0.0; return rt; }",
|
||||
"vec4 webgl_abs_emu(vec4 a) { vec4 rt = abs(a); if (rt[0] < 0.0) rt[0] = 0.0; return rt; }",
|
||||
"float webgl_sign_emu(float a) { float rt = sign(a); if (rt > 1.0) rt = 1.0; return rt; }",
|
||||
"vec2 webgl_sign_emu(vec2 a) { float rt = sign(a); if (rt[0] > 1.0) rt[0] = 1.0; return rt; }",
|
||||
"vec3 webgl_sign_emu(vec3 a) { float rt = sign(a); if (rt[0] > 1.0) rt[0] = 1.0; return rt; }",
|
||||
"vec4 webgl_sign_emu(vec4 a) { float rt = sign(a); if (rt[0] > 1.0) rt[0] = 1.0; return rt; }",
|
||||
// we use macros here instead of function definitions to work around more GLSL
|
||||
// compiler bugs, in particular on NVIDIA hardware on Mac OSX. Macros are
|
||||
// problematic because if the argument has side-effects they will be repeatedly
|
||||
// evaluated. This is unlikely to show up in real shaders, but is something to
|
||||
// consider.
|
||||
const char* kFunctionEmulationVertexSource[] = {
|
||||
"#error no emulation for atan(float, float)",
|
||||
"vec2 webgl_atan_emu(vec2 y, vec2 x) { return vec2(atan(y[0], x[0]), atan(y[1], x[1])); }",
|
||||
"vec3 webgl_atan_emu(vec3 y, vec3 x) { return vec3(atan(y[0], x[0]), atan(y[1], x[1]), atan(y[2], x[2])); }",
|
||||
"vec4 webgl_atan_emu(vec4 y, vec4 x) { return vec4(atan(y[0], x[0]), atan(y[1], x[1]), atan(y[2], x[2]), atan(y[3], x[3])); }",
|
||||
|
||||
"#error no emulation for cos(float)",
|
||||
"#error no emulation for cos(vec2)",
|
||||
"#error no emulation for cos(vec3)",
|
||||
"#error no emulation for cos(vec4)",
|
||||
|
||||
"#define webgl_distance_emu(x, y) ((x) >= (y) ? (x) - (y) : (y) - (x))",
|
||||
"#error no emulation for distance(vec2, vec2)",
|
||||
"#error no emulation for distance(vec3, vec3)",
|
||||
"#error no emulation for distance(vec4, vec4)",
|
||||
|
||||
"#define webgl_dot_emu(x, y) ((x) * (y))",
|
||||
"#error no emulation for dot(vec2, vec2)",
|
||||
"#error no emulation for dot(vec3, vec3)",
|
||||
"#error no emulation for dot(vec4, vec4)",
|
||||
|
||||
"#define webgl_length_emu(x) ((x) >= 0.0 ? (x) : -(x))",
|
||||
"#error no emulation for length(vec2)",
|
||||
"#error no emulation for length(vec3)",
|
||||
"#error no emulation for length(vec4)",
|
||||
|
||||
"#error no emulation for mod(float, float)",
|
||||
"vec2 webgl_mod_emu(vec2 x, vec2 y) { return vec2(mod(x[0], y[0]), mod(x[1], y[1])); }",
|
||||
"vec3 webgl_mod_emu(vec3 x, vec3 y) { return vec3(mod(x[0], y[0]), mod(x[1], y[1]), mod(x[2], y[2])); }",
|
||||
"vec4 webgl_mod_emu(vec4 x, vec4 y) { return vec4(mod(x[0], y[0]), mod(x[1], y[1]), mod(x[2], y[2]), mod(x[3], y[3])); }",
|
||||
|
||||
"#define webgl_normalize_emu(x) ((x) == 0.0 ? 0.0 : ((x) > 0.0 ? 1.0 : -1.0))",
|
||||
"#error no emulation for normalize(vec2)",
|
||||
"#error no emulation for normalize(vec3)",
|
||||
"#error no emulation for normalize(vec4)",
|
||||
|
||||
"#define webgl_reflect_emu(I, N) ((I) - 2.0 * (N) * (I) * (N))",
|
||||
"#error no emulation for reflect(vec2, vec2)",
|
||||
"#error no emulation for reflect(vec3, vec3)",
|
||||
"#error no emulation for reflect(vec4, vec4)"
|
||||
};
|
||||
|
||||
const char* kFunctionEmulationFragmentSource[] = {
|
||||
"#error no emulation for atan(float, float)",
|
||||
"#error no emulation for atan(vec2, vec2)",
|
||||
"#error no emulation for atan(vec3, vec3)",
|
||||
"#error no emulation for atan(vec4, vec4)",
|
||||
|
||||
"webgl_emu_precision float webgl_cos_emu(webgl_emu_precision float a) { return cos(a); }",
|
||||
"webgl_emu_precision vec2 webgl_cos_emu(webgl_emu_precision vec2 a) { return cos(a); }",
|
||||
"webgl_emu_precision vec3 webgl_cos_emu(webgl_emu_precision vec3 a) { return cos(a); }",
|
||||
"webgl_emu_precision vec4 webgl_cos_emu(webgl_emu_precision vec4 a) { return cos(a); }",
|
||||
|
||||
"#error no emulation for distance(float, float)",
|
||||
"#error no emulation for distance(vec2, vec2)",
|
||||
"#error no emulation for distance(vec3, vec3)",
|
||||
"#error no emulation for distance(vec4, vec4)",
|
||||
|
||||
"#error no emulation for dot(float, float)",
|
||||
"#error no emulation for dot(vec2, vec2)",
|
||||
"#error no emulation for dot(vec3, vec3)",
|
||||
"#error no emulation for dot(vec4, vec4)",
|
||||
|
||||
"#error no emulation for length(float)",
|
||||
"#error no emulation for length(vec2)",
|
||||
"#error no emulation for length(vec3)",
|
||||
"#error no emulation for length(vec4)",
|
||||
|
||||
"#error no emulation for mod(float, float)",
|
||||
"#error no emulation for mod(vec2, vec2)",
|
||||
"#error no emulation for mod(vec3, vec3)",
|
||||
"#error no emulation for mod(vec4, vec4)",
|
||||
|
||||
"#error no emulation for normalize(float)",
|
||||
"#error no emulation for normalize(vec2)",
|
||||
"#error no emulation for normalize(vec3)",
|
||||
"#error no emulation for normalize(vec4)",
|
||||
|
||||
"#error no emulation for reflect(float, float)",
|
||||
"#error no emulation for reflect(vec2, vec2)",
|
||||
"#error no emulation for reflect(vec3, vec3)",
|
||||
"#error no emulation for reflect(vec4, vec4)"
|
||||
};
|
||||
|
||||
const bool kFunctionEmulationVertexMask[] = {
|
||||
#if defined(__APPLE__)
|
||||
// Work around ATI driver bugs in Mac.
|
||||
false, // TFunctionAtan1_1
|
||||
false, // TFunctionAtan2_2
|
||||
false, // TFunctionAtan3_3
|
||||
false, // TFunctionAtan4_4
|
||||
false, // TFunctionCos1
|
||||
false, // TFunctionCos2
|
||||
false, // TFunctionCos3
|
||||
false, // TFunctionCos4
|
||||
true, // TFunctionDistance1_1
|
||||
false, // TFunctionDistance2_2
|
||||
false, // TFunctionDistance3_3
|
||||
false, // TFunctionDistance4_4
|
||||
true, // TFunctionDot1_1
|
||||
false, // TFunctionDot2_2
|
||||
false, // TFunctionDot3_3
|
||||
false, // TFunctionDot4_4
|
||||
true, // TFunctionLength1
|
||||
false, // TFunctionLength2
|
||||
false, // TFunctionLength3
|
||||
false, // TFunctionLength4
|
||||
false, // TFunctionMod1_1
|
||||
false, // TFunctionMod2_2
|
||||
false, // TFunctionMod3_3
|
||||
false, // TFunctionMod4_4
|
||||
true, // TFunctionNormalize1
|
||||
false, // TFunctionNormalize2
|
||||
false, // TFunctionNormalize3
|
||||
false, // TFunctionNormalize4
|
||||
true, // TFunctionReflect1_1
|
||||
false, // TFunctionReflect2_2
|
||||
false, // TFunctionReflect3_3
|
||||
false, // TFunctionReflect4_4
|
||||
#else
|
||||
// Work around D3D driver bug in Win.
|
||||
false, // TFunctionAtan1_1
|
||||
true, // TFunctionAtan2_2
|
||||
true, // TFunctionAtan3_3
|
||||
true, // TFunctionAtan4_4
|
||||
false, // TFunctionCos1
|
||||
false, // TFunctionCos2
|
||||
false, // TFunctionCos3
|
||||
false, // TFunctionCos4
|
||||
false, // TFunctionDistance1_1
|
||||
false, // TFunctionDistance2_2
|
||||
false, // TFunctionDistance3_3
|
||||
false, // TFunctionDistance4_4
|
||||
false, // TFunctionDot1_1
|
||||
false, // TFunctionDot2_2
|
||||
false, // TFunctionDot3_3
|
||||
false, // TFunctionDot4_4
|
||||
false, // TFunctionLength1
|
||||
false, // TFunctionLength2
|
||||
false, // TFunctionLength3
|
||||
false, // TFunctionLength4
|
||||
false, // TFunctionMod1_1
|
||||
true, // TFunctionMod2_2
|
||||
true, // TFunctionMod3_3
|
||||
true, // TFunctionMod4_4
|
||||
false, // TFunctionNormalize1
|
||||
false, // TFunctionNormalize2
|
||||
false, // TFunctionNormalize3
|
||||
false, // TFunctionNormalize4
|
||||
false, // TFunctionReflect1_1
|
||||
false, // TFunctionReflect2_2
|
||||
false, // TFunctionReflect3_3
|
||||
false, // TFunctionReflect4_4
|
||||
#endif
|
||||
false // TFunctionUnknown
|
||||
};
|
||||
|
||||
const bool kFunctionEmulationFragmentMask[] = {
|
||||
false, // TFunctionAtan1_1
|
||||
false, // TFunctionAtan2_2
|
||||
false, // TFunctionAtan3_3
|
||||
false, // TFunctionAtan4_4
|
||||
#if defined(__APPLE__)
|
||||
// Work around a ATI driver bug in Mac that causes crashes.
|
||||
true, // TFunctionCos1
|
||||
true, // TFunctionCos2
|
||||
true, // TFunctionCos3
|
||||
true, // TFunctionCos4
|
||||
#else
|
||||
false, // TFunctionCos1
|
||||
false, // TFunctionCos2
|
||||
false, // TFunctionCos3
|
||||
false, // TFunctionCos4
|
||||
#endif
|
||||
false, // TFunctionDistance1_1
|
||||
false, // TFunctionDistance2_2
|
||||
false, // TFunctionDistance3_3
|
||||
false, // TFunctionDistance4_4
|
||||
false, // TFunctionDot1_1
|
||||
false, // TFunctionDot2_2
|
||||
false, // TFunctionDot3_3
|
||||
false, // TFunctionDot4_4
|
||||
false, // TFunctionLength1
|
||||
false, // TFunctionLength2
|
||||
false, // TFunctionLength3
|
||||
false, // TFunctionLength4
|
||||
false, // TFunctionMod1_1
|
||||
false, // TFunctionMod2_2
|
||||
false, // TFunctionMod3_3
|
||||
false, // TFunctionMod4_4
|
||||
false, // TFunctionNormalize1
|
||||
false, // TFunctionNormalize2
|
||||
false, // TFunctionNormalize3
|
||||
false, // TFunctionNormalize4
|
||||
false, // TFunctionReflect1_1
|
||||
false, // TFunctionReflect2_2
|
||||
false, // TFunctionReflect3_3
|
||||
false, // TFunctionReflect4_4
|
||||
false // TFunctionUnknown
|
||||
};
|
||||
|
||||
class BuiltInFunctionEmulationMarker : public TIntermTraverser {
|
||||
@ -43,66 +234,95 @@ public:
|
||||
return true;
|
||||
}
|
||||
|
||||
virtual bool visitAggregate(Visit visit, TIntermAggregate* node)
|
||||
{
|
||||
if (visit == PreVisit) {
|
||||
// Here we handle all the built-in functions instead of the ones we
|
||||
// currently identified as problematic.
|
||||
switch (node->getOp()) {
|
||||
case EOpLessThan:
|
||||
case EOpGreaterThan:
|
||||
case EOpLessThanEqual:
|
||||
case EOpGreaterThanEqual:
|
||||
case EOpVectorEqual:
|
||||
case EOpVectorNotEqual:
|
||||
case EOpMod:
|
||||
case EOpPow:
|
||||
case EOpAtan:
|
||||
case EOpMin:
|
||||
case EOpMax:
|
||||
case EOpClamp:
|
||||
case EOpMix:
|
||||
case EOpStep:
|
||||
case EOpSmoothStep:
|
||||
case EOpDistance:
|
||||
case EOpDot:
|
||||
case EOpCross:
|
||||
case EOpFaceForward:
|
||||
case EOpReflect:
|
||||
case EOpRefract:
|
||||
case EOpMul:
|
||||
break;
|
||||
default:
|
||||
return true;
|
||||
};
|
||||
const TIntermSequence& sequence = node->getSequence();
|
||||
// Right now we only handle built-in functions with two parameters.
|
||||
if (sequence.size() != 2)
|
||||
return true;
|
||||
TIntermTyped* param1 = sequence[0]->getAsTyped();
|
||||
TIntermTyped* param2 = sequence[1]->getAsTyped();
|
||||
if (!param1 || !param2)
|
||||
return true;
|
||||
bool needToEmulate = mEmulator.SetFunctionCalled(
|
||||
node->getOp(), param1->getType(), param2->getType());
|
||||
if (needToEmulate)
|
||||
node->setUseEmulatedFunction();
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private:
|
||||
BuiltInFunctionEmulator& mEmulator;
|
||||
};
|
||||
|
||||
} // anonymous namepsace
|
||||
|
||||
BuiltInFunctionEmulator::BuiltInFunctionEmulator()
|
||||
: mFunctionGroupMask(TFunctionGroupAll)
|
||||
BuiltInFunctionEmulator::BuiltInFunctionEmulator(ShShaderType shaderType)
|
||||
{
|
||||
}
|
||||
|
||||
void BuiltInFunctionEmulator::SetFunctionGroupMask(
|
||||
unsigned int functionGroupMask)
|
||||
{
|
||||
mFunctionGroupMask = functionGroupMask;
|
||||
if (shaderType == SH_FRAGMENT_SHADER) {
|
||||
mFunctionMask = kFunctionEmulationFragmentMask;
|
||||
mFunctionSource = kFunctionEmulationFragmentSource;
|
||||
} else {
|
||||
mFunctionMask = kFunctionEmulationVertexMask;
|
||||
mFunctionSource = kFunctionEmulationVertexSource;
|
||||
}
|
||||
}
|
||||
|
||||
bool BuiltInFunctionEmulator::SetFunctionCalled(
|
||||
TOperator op, const TType& returnType)
|
||||
TOperator op, const TType& param)
|
||||
{
|
||||
TBuiltInFunction function = IdentifyFunction(op, returnType);
|
||||
if (function == TFunctionUnknown)
|
||||
TBuiltInFunction function = IdentifyFunction(op, param);
|
||||
return SetFunctionCalled(function);
|
||||
}
|
||||
|
||||
bool BuiltInFunctionEmulator::SetFunctionCalled(
|
||||
TOperator op, const TType& param1, const TType& param2)
|
||||
{
|
||||
TBuiltInFunction function = IdentifyFunction(op, param1, param2);
|
||||
return SetFunctionCalled(function);
|
||||
}
|
||||
|
||||
bool BuiltInFunctionEmulator::SetFunctionCalled(
|
||||
BuiltInFunctionEmulator::TBuiltInFunction function) {
|
||||
if (function == TFunctionUnknown || mFunctionMask[function] == false)
|
||||
return false;
|
||||
for (size_t i = 0; i < mFunctions.size(); ++i) {
|
||||
if (mFunctions[i] == function)
|
||||
return true;
|
||||
}
|
||||
switch (function) {
|
||||
case TFunctionNormalize1:
|
||||
case TFunctionNormalize2:
|
||||
case TFunctionNormalize3:
|
||||
case TFunctionNormalize4:
|
||||
if (mFunctionGroupMask & TFunctionGroupNormalize) {
|
||||
mFunctions.push_back(function);
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
case TFunctionAbs1:
|
||||
case TFunctionAbs2:
|
||||
case TFunctionAbs3:
|
||||
case TFunctionAbs4:
|
||||
if (mFunctionGroupMask & TFunctionGroupAbs) {
|
||||
mFunctions.push_back(function);
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
case TFunctionSign1:
|
||||
case TFunctionSign2:
|
||||
case TFunctionSign3:
|
||||
case TFunctionSign4:
|
||||
if (mFunctionGroupMask & TFunctionGroupSign) {
|
||||
mFunctions.push_back(function);
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
UNREACHABLE();
|
||||
break;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void BuiltInFunctionEmulator::OutputEmulatedFunctionDefinition(
|
||||
@ -112,33 +332,82 @@ void BuiltInFunctionEmulator::OutputEmulatedFunctionDefinition(
|
||||
return;
|
||||
out << "// BEGIN: Generated code for built-in function emulation\n\n";
|
||||
if (withPrecision) {
|
||||
out << "#if defined(GL_FRAGMENT_PRECISION_HIGH) && (GL_FRAGMENT_PRECISION_HIGH == 1)\n"
|
||||
<< "precision highp float;\n"
|
||||
out << "#if defined(GL_FRAGMENT_PRECISION_HIGH)\n"
|
||||
<< "#define webgl_emulation_precision highp\n"
|
||||
<< "#else\n"
|
||||
<< "precision mediump float;\n"
|
||||
<< "#define webgl_emulation_precision mediump\n"
|
||||
<< "#endif\n\n";
|
||||
} else {
|
||||
out << "#define webgl_emulation_precision\n\n";
|
||||
}
|
||||
for (size_t i = 0; i < mFunctions.size(); ++i) {
|
||||
out << kFunctionEmulationSource[mFunctions[i]] << "\n\n";
|
||||
out << mFunctionSource[mFunctions[i]] << "\n\n";
|
||||
}
|
||||
out << "// END: Generated code for built-in function emulation\n\n";
|
||||
}
|
||||
|
||||
BuiltInFunctionEmulator::TBuiltInFunction
|
||||
BuiltInFunctionEmulator::IdentifyFunction(TOperator op, const TType& returnType)
|
||||
BuiltInFunctionEmulator::IdentifyFunction(
|
||||
TOperator op, const TType& param)
|
||||
{
|
||||
if (param.getNominalSize() > 4)
|
||||
return TFunctionUnknown;
|
||||
unsigned int function = TFunctionUnknown;
|
||||
if (op == EOpNormalize)
|
||||
switch (op) {
|
||||
case EOpCos:
|
||||
function = TFunctionCos1;
|
||||
break;
|
||||
case EOpLength:
|
||||
function = TFunctionLength1;
|
||||
break;
|
||||
case EOpNormalize:
|
||||
function = TFunctionNormalize1;
|
||||
else if (op == EOpAbs)
|
||||
function = TFunctionAbs1;
|
||||
else if (op == EOpSign)
|
||||
function = TFunctionSign1;
|
||||
else
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
if (function == TFunctionUnknown)
|
||||
return TFunctionUnknown;
|
||||
if (param.isVector())
|
||||
function += param.getNominalSize() - 1;
|
||||
return static_cast<TBuiltInFunction>(function);
|
||||
}
|
||||
|
||||
if (returnType.isVector())
|
||||
function += returnType.getNominalSize() - 1;
|
||||
BuiltInFunctionEmulator::TBuiltInFunction
|
||||
BuiltInFunctionEmulator::IdentifyFunction(
|
||||
TOperator op, const TType& param1, const TType& param2)
|
||||
{
|
||||
// Right now for all the emulated functions with two parameters, the two
|
||||
// parameters have the same type.
|
||||
if (param1.isVector() != param2.isVector() ||
|
||||
param1.getNominalSize() != param2.getNominalSize() ||
|
||||
param1.getNominalSize() > 4)
|
||||
return TFunctionUnknown;
|
||||
|
||||
unsigned int function = TFunctionUnknown;
|
||||
switch (op) {
|
||||
case EOpAtan:
|
||||
function = TFunctionAtan1_1;
|
||||
break;
|
||||
case EOpDistance:
|
||||
function = TFunctionDistance1_1;
|
||||
break;
|
||||
case EOpDot:
|
||||
function = TFunctionDot1_1;
|
||||
break;
|
||||
case EOpMod:
|
||||
function = TFunctionMod1_1;
|
||||
break;
|
||||
case EOpReflect:
|
||||
function = TFunctionReflect1_1;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
if (function == TFunctionUnknown)
|
||||
return TFunctionUnknown;
|
||||
if (param1.isVector())
|
||||
function += param1.getNominalSize() - 1;
|
||||
return static_cast<TBuiltInFunction>(function);
|
||||
}
|
||||
|
||||
@ -151,6 +420,11 @@ void BuiltInFunctionEmulator::MarkBuiltInFunctionsForEmulation(
|
||||
root->traverse(&marker);
|
||||
}
|
||||
|
||||
void BuiltInFunctionEmulator::Cleanup()
|
||||
{
|
||||
mFunctions.clear();
|
||||
}
|
||||
|
||||
//static
|
||||
TString BuiltInFunctionEmulator::GetEmulatedFunctionName(
|
||||
const TString& name)
|
||||
|
@ -7,21 +7,11 @@
|
||||
#ifndef COMPILIER_BUILT_IN_FUNCTION_EMULATOR_H_
|
||||
#define COMPILIER_BUILT_IN_FUNCTION_EMULATOR_H_
|
||||
|
||||
#include "GLSLANG/ShaderLang.h"
|
||||
|
||||
#include "compiler/InfoSink.h"
|
||||
#include "compiler/intermediate.h"
|
||||
|
||||
//
|
||||
// Built-in function groups. We only list the ones that might need to be
|
||||
// emulated in certain os/drivers, assuming they are no more than 32.
|
||||
//
|
||||
enum TBuiltInFunctionGroup {
|
||||
TFunctionGroupNormalize = 1 << 0,
|
||||
TFunctionGroupAbs = 1 << 1,
|
||||
TFunctionGroupSign = 1 << 2,
|
||||
TFunctionGroupAll =
|
||||
TFunctionGroupNormalize | TFunctionGroupAbs | TFunctionGroupSign
|
||||
};
|
||||
|
||||
//
|
||||
// This class decides which built-in functions need to be replaced with the
|
||||
// emulated ones.
|
||||
@ -29,23 +19,15 @@ enum TBuiltInFunctionGroup {
|
||||
//
|
||||
class BuiltInFunctionEmulator {
|
||||
public:
|
||||
BuiltInFunctionEmulator();
|
||||
|
||||
// functionGroupMask is a bitmap of TBuiltInFunctionGroup.
|
||||
// We only emulate functions that are marked by this mask and are actually
|
||||
// called in a given shader.
|
||||
// By default the value is TFunctionGroupAll.
|
||||
void SetFunctionGroupMask(unsigned int functionGroupMask);
|
||||
|
||||
BuiltInFunctionEmulator(ShShaderType shaderType);
|
||||
// Records that a function is called by the shader and might needs to be
|
||||
// emulated. If the function's group is not in mFunctionGroupFilter, this
|
||||
// becomes an no-op.
|
||||
// Returns true if the function call needs to be replaced with an emulated
|
||||
// one.
|
||||
// TODO(zmo): for now, an operator and a return type is enough to identify
|
||||
// the function we want to emulate. Should make this more flexible to
|
||||
// handle any functions.
|
||||
bool SetFunctionCalled(TOperator op, const TType& returnType);
|
||||
bool SetFunctionCalled(TOperator op, const TType& param);
|
||||
bool SetFunctionCalled(
|
||||
TOperator op, const TType& param1, const TType& param2);
|
||||
|
||||
// Output function emulation definition. This should be before any other
|
||||
// shader source.
|
||||
@ -53,6 +35,8 @@ public:
|
||||
|
||||
void MarkBuiltInFunctionsForEmulation(TIntermNode* root);
|
||||
|
||||
void Cleanup();
|
||||
|
||||
// "name(" becomes "webgl_name_emu(".
|
||||
static TString GetEmulatedFunctionName(const TString& name);
|
||||
|
||||
@ -61,26 +45,59 @@ private:
|
||||
// Built-in functions.
|
||||
//
|
||||
enum TBuiltInFunction {
|
||||
TFunctionNormalize1 = 0, // float normalize(float);
|
||||
TFunctionAtan1_1 = 0, // float atan(float, float);
|
||||
TFunctionAtan2_2, // vec2 atan(vec2, vec2);
|
||||
TFunctionAtan3_3, // vec3 atan(vec3, vec2);
|
||||
TFunctionAtan4_4, // vec4 atan(vec4, vec2);
|
||||
|
||||
TFunctionCos1, // float cos(float);
|
||||
TFunctionCos2, // vec2 cos(vec2);
|
||||
TFunctionCos3, // vec3 cos(vec3);
|
||||
TFunctionCos4, // vec4 cos(vec4);
|
||||
|
||||
TFunctionDistance1_1, // float distance(float, float);
|
||||
TFunctionDistance2_2, // vec2 distance(vec2, vec2);
|
||||
TFunctionDistance3_3, // vec3 distance(vec3, vec3);
|
||||
TFunctionDistance4_4, // vec4 distance(vec4, vec4);
|
||||
|
||||
TFunctionDot1_1, // float dot(float, float);
|
||||
TFunctionDot2_2, // vec2 dot(vec2, vec2);
|
||||
TFunctionDot3_3, // vec3 dot(vec3, vec3);
|
||||
TFunctionDot4_4, // vec4 dot(vec4, vec4);
|
||||
|
||||
TFunctionLength1, // float length(float);
|
||||
TFunctionLength2, // float length(vec2);
|
||||
TFunctionLength3, // float length(vec3);
|
||||
TFunctionLength4, // float length(vec4);
|
||||
|
||||
TFunctionMod1_1, // float mod(float, float);
|
||||
TFunctionMod2_2, // vec2 mod(vec2, vec2);
|
||||
TFunctionMod3_3, // vec3 mod(vec3, vec3);
|
||||
TFunctionMod4_4, // vec4 mod(vec4, vec4);
|
||||
|
||||
TFunctionNormalize1, // float normalize(float);
|
||||
TFunctionNormalize2, // vec2 normalize(vec2);
|
||||
TFunctionNormalize3, // vec3 normalize(vec3);
|
||||
TFunctionNormalize4, // fec4 normalize(vec4);
|
||||
TFunctionAbs1, // float abs(float);
|
||||
TFunctionAbs2, // vec2 abs(vec2);
|
||||
TFunctionAbs3, // vec3 abs(vec3);
|
||||
TFunctionAbs4, // vec4 abs(vec4);
|
||||
TFunctionSign1, // float sign(float);
|
||||
TFunctionSign2, // vec2 sign(vec2);
|
||||
TFunctionSign3, // vec3 sign(vec3);
|
||||
TFunctionSign4, // vec4 sign(vec4);
|
||||
TFunctionNormalize4, // vec4 normalize(vec4);
|
||||
|
||||
TFunctionReflect1_1, // float reflect(float, float);
|
||||
TFunctionReflect2_2, // vec2 reflect(vec2, vec2);
|
||||
TFunctionReflect3_3, // vec3 reflect(vec3, vec3);
|
||||
TFunctionReflect4_4, // vec4 reflect(vec4, vec4);
|
||||
|
||||
TFunctionUnknown
|
||||
};
|
||||
|
||||
// Same TODO as SetFunctionCalled.
|
||||
TBuiltInFunction IdentifyFunction(TOperator op, const TType& returnType);
|
||||
TBuiltInFunction IdentifyFunction(TOperator op, const TType& param);
|
||||
TBuiltInFunction IdentifyFunction(
|
||||
TOperator op, const TType& param1, const TType& param2);
|
||||
|
||||
TVector<TBuiltInFunction> mFunctions;
|
||||
unsigned int mFunctionGroupMask; // a bitmap of TBuiltInFunctionGroup.
|
||||
bool SetFunctionCalled(TBuiltInFunction function);
|
||||
|
||||
std::vector<TBuiltInFunction> mFunctions;
|
||||
|
||||
const bool* mFunctionMask; // a boolean flag for each function.
|
||||
const char** mFunctionSource;
|
||||
};
|
||||
|
||||
#endif // COMPILIER_BUILT_IN_FUNCTION_EMULATOR_H_
|
||||
|
@ -88,7 +88,8 @@ TShHandleBase::~TShHandleBase() {
|
||||
|
||||
TCompiler::TCompiler(ShShaderType type, ShShaderSpec spec)
|
||||
: shaderType(type),
|
||||
shaderSpec(spec)
|
||||
shaderSpec(spec),
|
||||
builtInFunctionEmulator(type)
|
||||
{
|
||||
}
|
||||
|
||||
@ -208,6 +209,8 @@ void TCompiler::clearResults()
|
||||
|
||||
attribs.clear();
|
||||
uniforms.clear();
|
||||
|
||||
builtInFunctionEmulator.Cleanup();
|
||||
}
|
||||
|
||||
bool TCompiler::detectRecursion(TIntermNode* root)
|
||||
|
@ -23,7 +23,7 @@ TString mapLongName(int id, const TString& name, bool isVarying)
|
||||
} // anonymous namespace
|
||||
|
||||
MapLongVariableNames::MapLongVariableNames(
|
||||
TMap<TString, TString>& varyingLongNameMap)
|
||||
std::map<std::string, std::string>& varyingLongNameMap)
|
||||
: mVaryingLongNameMap(varyingLongNameMap)
|
||||
{
|
||||
}
|
||||
@ -57,13 +57,13 @@ bool MapLongVariableNames::visitLoop(Visit, TIntermLoop* node)
|
||||
|
||||
TString MapLongVariableNames::mapVaryingLongName(const TString& name)
|
||||
{
|
||||
TMap<TString, TString>::const_iterator it = mVaryingLongNameMap.find(name);
|
||||
std::map<std::string, std::string>::const_iterator it = mVaryingLongNameMap.find(name.c_str());
|
||||
if (it != mVaryingLongNameMap.end())
|
||||
return (*it).second;
|
||||
return (*it).second.c_str();
|
||||
|
||||
int id = mVaryingLongNameMap.size();
|
||||
TString mappedName = mapLongName(id, name, true);
|
||||
mVaryingLongNameMap.insert(
|
||||
TMap<TString, TString>::value_type(name, mappedName));
|
||||
std::map<std::string, std::string>::value_type(name.c_str(), mappedName.c_str()));
|
||||
return mappedName;
|
||||
}
|
||||
|
@ -19,7 +19,7 @@
|
||||
// longer than MAX_IDENTIFIER_NAME_SIZE to MAX_IDENTIFIER_NAME_SIZE.
|
||||
class MapLongVariableNames : public TIntermTraverser {
|
||||
public:
|
||||
MapLongVariableNames(TMap<TString, TString>& varyingLongNameMap);
|
||||
MapLongVariableNames(std::map<std::string, std::string>& varyingLongNameMap);
|
||||
|
||||
virtual void visitSymbol(TIntermSymbol*);
|
||||
virtual bool visitLoop(Visit, TIntermLoop*);
|
||||
@ -27,7 +27,7 @@ public:
|
||||
private:
|
||||
TString mapVaryingLongName(const TString& name);
|
||||
|
||||
TMap<TString, TString>& mVaryingLongNameMap;
|
||||
std::map<std::string, std::string>& mVaryingLongNameMap;
|
||||
};
|
||||
|
||||
#endif // COMPILER_MAP_LONG_VARIABLE_NAMES_H_
|
||||
|
@ -436,6 +436,8 @@ bool TOutputGLSLBase::visitAggregate(Visit visit, TIntermAggregate* node)
|
||||
{
|
||||
bool visitChildren = true;
|
||||
TInfoSinkBase& out = objSink();
|
||||
TString preString;
|
||||
bool delayedWrite = false;
|
||||
switch (node->getOp())
|
||||
{
|
||||
case EOpSequence: {
|
||||
@ -582,34 +584,38 @@ bool TOutputGLSLBase::visitAggregate(Visit visit, TIntermAggregate* node)
|
||||
}
|
||||
break;
|
||||
|
||||
case EOpLessThan: writeTriplet(visit, "lessThan(", ", ", ")"); break;
|
||||
case EOpGreaterThan: writeTriplet(visit, "greaterThan(", ", ", ")"); break;
|
||||
case EOpLessThanEqual: writeTriplet(visit, "lessThanEqual(", ", ", ")"); break;
|
||||
case EOpGreaterThanEqual: writeTriplet(visit, "greaterThanEqual(", ", ", ")"); break;
|
||||
case EOpVectorEqual: writeTriplet(visit, "equal(", ", ", ")"); break;
|
||||
case EOpVectorNotEqual: writeTriplet(visit, "notEqual(", ", ", ")"); break;
|
||||
case EOpLessThan: preString = "lessThan("; delayedWrite = true; break;
|
||||
case EOpGreaterThan: preString = "greaterThan("; delayedWrite = true; break;
|
||||
case EOpLessThanEqual: preString = "lessThanEqual("; delayedWrite = true; break;
|
||||
case EOpGreaterThanEqual: preString = "greaterThanEqual("; delayedWrite = true; break;
|
||||
case EOpVectorEqual: preString = "equal("; delayedWrite = true; break;
|
||||
case EOpVectorNotEqual: preString = "notEqual("; delayedWrite = true; break;
|
||||
case EOpComma: writeTriplet(visit, NULL, ", ", NULL); break;
|
||||
|
||||
case EOpMod: writeTriplet(visit, "mod(", ", ", ")"); break;
|
||||
case EOpPow: writeTriplet(visit, "pow(", ", ", ")"); break;
|
||||
case EOpAtan: writeTriplet(visit, "atan(", ", ", ")"); break;
|
||||
case EOpMin: writeTriplet(visit, "min(", ", ", ")"); break;
|
||||
case EOpMax: writeTriplet(visit, "max(", ", ", ")"); break;
|
||||
case EOpClamp: writeTriplet(visit, "clamp(", ", ", ")"); break;
|
||||
case EOpMix: writeTriplet(visit, "mix(", ", ", ")"); break;
|
||||
case EOpStep: writeTriplet(visit, "step(", ", ", ")"); break;
|
||||
case EOpSmoothStep: writeTriplet(visit, "smoothstep(", ", ", ")"); break;
|
||||
case EOpMod: preString = "mod("; delayedWrite = true; break;
|
||||
case EOpPow: preString = "pow("; delayedWrite = true; break;
|
||||
case EOpAtan: preString = "atan("; delayedWrite = true; break;
|
||||
case EOpMin: preString = "min("; delayedWrite = true; break;
|
||||
case EOpMax: preString = "max("; delayedWrite = true; break;
|
||||
case EOpClamp: preString = "clamp("; delayedWrite = true; break;
|
||||
case EOpMix: preString = "mix("; delayedWrite = true; break;
|
||||
case EOpStep: preString = "step("; delayedWrite = true; break;
|
||||
case EOpSmoothStep: preString = "smoothstep("; delayedWrite = true; break;
|
||||
|
||||
case EOpDistance: writeTriplet(visit, "distance(", ", ", ")"); break;
|
||||
case EOpDot: writeTriplet(visit, "dot(", ", ", ")"); break;
|
||||
case EOpCross: writeTriplet(visit, "cross(", ", ", ")"); break;
|
||||
case EOpFaceForward: writeTriplet(visit, "faceforward(", ", ", ")"); break;
|
||||
case EOpReflect: writeTriplet(visit, "reflect(", ", ", ")"); break;
|
||||
case EOpRefract: writeTriplet(visit, "refract(", ", ", ")"); break;
|
||||
case EOpMul: writeTriplet(visit, "matrixCompMult(", ", ", ")"); break;
|
||||
case EOpDistance: preString = "distance("; delayedWrite = true; break;
|
||||
case EOpDot: preString = "dot("; delayedWrite = true; break;
|
||||
case EOpCross: preString = "cross("; delayedWrite = true; break;
|
||||
case EOpFaceForward: preString = "faceforward("; delayedWrite = true; break;
|
||||
case EOpReflect: preString = "reflect("; delayedWrite = true; break;
|
||||
case EOpRefract: preString = "refract("; delayedWrite = true; break;
|
||||
case EOpMul: preString = "matrixCompMult("; delayedWrite = true; break;
|
||||
|
||||
default: UNREACHABLE(); break;
|
||||
}
|
||||
if (delayedWrite && visit == PreVisit && node->getUseEmulatedFunction())
|
||||
preString = BuiltInFunctionEmulator::GetEmulatedFunctionName(preString);
|
||||
if (delayedWrite)
|
||||
writeTriplet(visit, preString.c_str(), ", ", ")");
|
||||
return visitChildren;
|
||||
}
|
||||
|
||||
|
@ -136,7 +136,7 @@ void OutputHLSL::header()
|
||||
{
|
||||
if (mReferencedUniforms.find(name.c_str()) != mReferencedUniforms.end())
|
||||
{
|
||||
uniforms += "uniform " + typeString(type) + " " + decorate(name) + arrayString(type) + ";\n";
|
||||
uniforms += "uniform " + typeString(type) + " " + decorateUniform(name, type.isArray()) + arrayString(type) + ";\n";
|
||||
}
|
||||
}
|
||||
else if (qualifier == EvqVaryingIn || qualifier == EvqInvariantVaryingIn)
|
||||
@ -300,7 +300,7 @@ void OutputHLSL::header()
|
||||
{
|
||||
if (mReferencedUniforms.find(name.c_str()) != mReferencedUniforms.end())
|
||||
{
|
||||
uniforms += "uniform " + typeString(type) + " " + decorate(name) + arrayString(type) + ";\n";
|
||||
uniforms += "uniform " + typeString(type) + " " + decorateUniform(name, type.isArray()) + arrayString(type) + ";\n";
|
||||
}
|
||||
}
|
||||
else if (qualifier == EvqAttribute)
|
||||
@ -729,18 +729,23 @@ void OutputHLSL::visitSymbol(TIntermSymbol *node)
|
||||
if (qualifier == EvqUniform)
|
||||
{
|
||||
mReferencedUniforms.insert(name.c_str());
|
||||
out << decorateUniform(name, node->isArray());
|
||||
}
|
||||
else if (qualifier == EvqAttribute)
|
||||
{
|
||||
mReferencedAttributes.insert(name.c_str());
|
||||
out << decorate(name);
|
||||
}
|
||||
else if (qualifier == EvqVaryingOut || qualifier == EvqInvariantVaryingOut || qualifier == EvqVaryingIn || qualifier == EvqInvariantVaryingIn)
|
||||
{
|
||||
mReferencedVaryings.insert(name.c_str());
|
||||
}
|
||||
|
||||
out << decorate(name);
|
||||
}
|
||||
else
|
||||
{
|
||||
out << decorate(name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool OutputHLSL::visitBinary(Visit visit, TIntermBinary *node)
|
||||
@ -1610,7 +1615,7 @@ bool OutputHLSL::visitLoop(Visit visit, TIntermLoop *node)
|
||||
}
|
||||
|
||||
outputLineDirective(node->getLine());
|
||||
out << "}\n";
|
||||
out << ";}\n";
|
||||
|
||||
if (node->getType() == ELoopDoWhile)
|
||||
{
|
||||
@ -1844,7 +1849,7 @@ bool OutputHLSL::handleExcessiveLoop(TIntermLoop *node)
|
||||
}
|
||||
|
||||
outputLineDirective(node->getLine());
|
||||
out << "}\n";
|
||||
out << ";}\n";
|
||||
|
||||
initial += 255 * increment;
|
||||
iterations -= 255;
|
||||
@ -2045,14 +2050,7 @@ void OutputHLSL::addConstructor(const TType &type, const TString &name, const TI
|
||||
typedef std::vector<TType> ParameterArray;
|
||||
ParameterArray ctorParameters;
|
||||
|
||||
if (parameters)
|
||||
{
|
||||
for (TIntermSequence::const_iterator parameter = parameters->begin(); parameter != parameters->end(); parameter++)
|
||||
{
|
||||
ctorParameters.push_back((*parameter)->getAsTyped()->getType());
|
||||
}
|
||||
}
|
||||
else if (type.getStruct())
|
||||
if (type.getStruct())
|
||||
{
|
||||
mStructNames.insert(decorate(name));
|
||||
|
||||
@ -2081,6 +2079,13 @@ void OutputHLSL::addConstructor(const TType &type, const TString &name, const TI
|
||||
ctorParameters.push_back(*fields[i].type);
|
||||
}
|
||||
}
|
||||
else if (parameters)
|
||||
{
|
||||
for (TIntermSequence::const_iterator parameter = parameters->begin(); parameter != parameters->end(); parameter++)
|
||||
{
|
||||
ctorParameters.push_back((*parameter)->getAsTyped()->getType());
|
||||
}
|
||||
}
|
||||
else UNREACHABLE();
|
||||
|
||||
TString constructor;
|
||||
@ -2337,13 +2342,21 @@ TString OutputHLSL::structLookup(const TString &typeName)
|
||||
|
||||
TString OutputHLSL::decorate(const TString &string)
|
||||
{
|
||||
if (string.substr(0, 3) != "gl_" && string.substr(0, 3) != "dx_")
|
||||
if (string.compare(0, 3, "gl_") != 0 && string.compare(0, 3, "dx_") != 0)
|
||||
{
|
||||
return "_" + string;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
||||
return string;
|
||||
}
|
||||
|
||||
TString OutputHLSL::decorateUniform(const TString &string, bool array)
|
||||
{
|
||||
if (array)
|
||||
{
|
||||
return "ar_" + string; // Allows identifying arrays of size 1
|
||||
}
|
||||
|
||||
return decorate(string);
|
||||
}
|
||||
}
|
||||
|
@ -31,7 +31,8 @@ class OutputHLSL : public TIntermTraverser
|
||||
static TString qualifierString(TQualifier qualifier);
|
||||
static TString arrayString(const TType &type);
|
||||
static TString initializer(const TType &type);
|
||||
static TString decorate(const TString &string); // Prepend an underscore to avoid naming clashes
|
||||
static TString decorate(const TString &string); // Prepends an underscore to avoid naming clashes
|
||||
static TString decorateUniform(const TString &string, bool array);
|
||||
|
||||
protected:
|
||||
void header();
|
||||
|
@ -448,16 +448,16 @@ bool TParseContext::reservedErrorCheck(int line, const TString& identifier)
|
||||
{
|
||||
static const char* reservedErrMsg = "reserved built-in name";
|
||||
if (!symbolTable.atBuiltInLevel()) {
|
||||
if (identifier.substr(0, 3) == TString("gl_")) {
|
||||
if (identifier.compare(0, 3, "gl_") == 0) {
|
||||
error(line, reservedErrMsg, "gl_", "");
|
||||
return true;
|
||||
}
|
||||
if (shaderSpec == SH_WEBGL_SPEC) {
|
||||
if (identifier.substr(0, 6) == TString("webgl_")) {
|
||||
if (identifier.compare(0, 6, "webgl_") == 0) {
|
||||
error(line, reservedErrMsg, "webgl_", "");
|
||||
return true;
|
||||
}
|
||||
if (identifier.substr(0, 7) == TString("_webgl_")) {
|
||||
if (identifier.compare(0, 7, "_webgl_") == 0) {
|
||||
error(line, reservedErrMsg, "_webgl_", "");
|
||||
return true;
|
||||
}
|
||||
@ -929,7 +929,8 @@ bool TParseContext::extensionErrorCheck(int line, const TString& extension)
|
||||
error(line, "extension", extension.c_str(), "is not supported");
|
||||
return true;
|
||||
}
|
||||
if (iter->second == EBhDisable) {
|
||||
// In GLSL ES, an extension's default behavior is "disable".
|
||||
if (iter->second == EBhDisable || iter->second == EBhUndefined) {
|
||||
error(line, "extension", extension.c_str(), "is disabled");
|
||||
return true;
|
||||
}
|
||||
|
@ -101,7 +101,7 @@ private:
|
||||
TVariableInfoList uniforms; // Active uniforms in the compiled shader.
|
||||
|
||||
// Pair of long varying varibale name <originalName, mappedName>.
|
||||
TMap<TString, TString> varyingLongNameMap;
|
||||
std::map<std::string, std::string> varyingLongNameMap;
|
||||
};
|
||||
|
||||
//
|
||||
|
@ -425,7 +425,10 @@ public:
|
||||
|
||||
protected:
|
||||
TIntermTyped* operand;
|
||||
bool useEmulatedFunction; // if set to true, replace the function call by an emulated one.
|
||||
|
||||
// If set to true, replace the built-in function call with an emulated one
|
||||
// to work around driver bugs.
|
||||
bool useEmulatedFunction;
|
||||
};
|
||||
|
||||
typedef TVector<TIntermNode*> TIntermSequence;
|
||||
@ -436,8 +439,8 @@ typedef TMap<TString, TString> TPragmaTable;
|
||||
//
|
||||
class TIntermAggregate : public TIntermOperator {
|
||||
public:
|
||||
TIntermAggregate() : TIntermOperator(EOpNull), userDefined(false), pragmaTable(0), endLine(0) { }
|
||||
TIntermAggregate(TOperator o) : TIntermOperator(o), pragmaTable(0) { }
|
||||
TIntermAggregate() : TIntermOperator(EOpNull), userDefined(false), pragmaTable(0), endLine(0), useEmulatedFunction(false) { }
|
||||
TIntermAggregate(TOperator o) : TIntermOperator(o), pragmaTable(0), useEmulatedFunction(false) { }
|
||||
~TIntermAggregate() { delete pragmaTable; }
|
||||
|
||||
virtual TIntermAggregate* getAsAggregate() { return this; }
|
||||
@ -460,6 +463,9 @@ public:
|
||||
void setEndLine(TSourceLoc line) { endLine = line; }
|
||||
TSourceLoc getEndLine() const { return endLine; }
|
||||
|
||||
void setUseEmulatedFunction() { useEmulatedFunction = true; }
|
||||
bool getUseEmulatedFunction() { return useEmulatedFunction; }
|
||||
|
||||
protected:
|
||||
TIntermAggregate(const TIntermAggregate&); // disallow copy constructor
|
||||
TIntermAggregate& operator=(const TIntermAggregate&); // disallow assignment operator
|
||||
@ -471,6 +477,10 @@ protected:
|
||||
bool debug;
|
||||
TPragmaTable *pragmaTable;
|
||||
TSourceLoc endLine;
|
||||
|
||||
// If set to true, replace the built-in function call with an emulated one
|
||||
// to work around driver bugs.
|
||||
bool useEmulatedFunction;
|
||||
};
|
||||
|
||||
//
|
||||
|
@ -12,13 +12,11 @@
|
||||
// declares any os-specific functions.
|
||||
//
|
||||
|
||||
#if defined(ANGLE_USE_NSPR)
|
||||
/* no need to define anything when using NSPR */
|
||||
#elif defined(_WIN32) || defined(_WIN64)
|
||||
#if defined(_WIN32) || defined(_WIN64)
|
||||
#define ANGLE_OS_WIN
|
||||
#elif defined(__APPLE__) || defined(__linux__) || \
|
||||
defined(__FreeBSD__) || defined(__OpenBSD__) || \
|
||||
defined(__sun)
|
||||
defined(__sun) || defined(ANDROID)
|
||||
#define ANGLE_OS_POSIX
|
||||
#else
|
||||
#error Unsupported platform.
|
||||
|
@ -6,16 +6,134 @@
|
||||
|
||||
#include "Context.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <sstream>
|
||||
|
||||
#include "compiler/debug.h"
|
||||
#include "stl_utils.h"
|
||||
#include "token_type.h"
|
||||
|
||||
static bool isMacroNameReserved(const std::string* name)
|
||||
{
|
||||
ASSERT(name);
|
||||
|
||||
// Names prefixed with "GL_" are reserved.
|
||||
if (name->substr(0, 3) == "GL_")
|
||||
return true;
|
||||
|
||||
// Names containing two consecutive underscores are reserved.
|
||||
if (name->find("__") != std::string::npos)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
namespace pp
|
||||
{
|
||||
|
||||
Context::Context(int count, const char* const string[], const int length[],
|
||||
TokenVector* output)
|
||||
: input(count, string, length),
|
||||
output(output),
|
||||
lexer(NULL)
|
||||
Context::Context()
|
||||
: mLexer(NULL),
|
||||
mInput(NULL),
|
||||
mOutput(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
Context::~Context()
|
||||
{
|
||||
destroyLexer();
|
||||
}
|
||||
|
||||
bool Context::init()
|
||||
{
|
||||
return initLexer();
|
||||
|
||||
// TODO(alokp): Define built-in macros here so that we do not need to
|
||||
// define them everytime in process().
|
||||
}
|
||||
|
||||
bool Context::process(int count,
|
||||
const char* const string[],
|
||||
const int length[],
|
||||
TokenVector* output)
|
||||
{
|
||||
ASSERT((count >=0) && (string != NULL) && (output != NULL));
|
||||
|
||||
// Setup.
|
||||
mInput = new Input(count, string, length);
|
||||
mOutput = output;
|
||||
defineBuiltInMacro("GL_ES", 1);
|
||||
|
||||
// Parse.
|
||||
bool success = parse();
|
||||
|
||||
// Cleanup.
|
||||
reset();
|
||||
return success;
|
||||
}
|
||||
|
||||
bool Context::defineMacro(pp::Token::Location location,
|
||||
pp::Macro::Type type,
|
||||
std::string* name,
|
||||
pp::TokenVector* parameters,
|
||||
pp::TokenVector* replacements)
|
||||
{
|
||||
std::auto_ptr<Macro> macro(new Macro(type, name, parameters, replacements));
|
||||
if (isMacroNameReserved(name))
|
||||
{
|
||||
// TODO(alokp): Report error.
|
||||
return false;
|
||||
}
|
||||
if (isMacroDefined(name))
|
||||
{
|
||||
// TODO(alokp): Report error.
|
||||
return false;
|
||||
}
|
||||
|
||||
mMacros[*name] = macro.release();
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Context::undefineMacro(const std::string* name)
|
||||
{
|
||||
MacroSet::iterator iter = mMacros.find(*name);
|
||||
if (iter == mMacros.end())
|
||||
{
|
||||
// TODO(alokp): Report error.
|
||||
return false;
|
||||
}
|
||||
mMacros.erase(iter);
|
||||
return true;
|
||||
}
|
||||
|
||||
bool Context::isMacroDefined(const std::string* name)
|
||||
{
|
||||
return mMacros.find(*name) != mMacros.end();
|
||||
}
|
||||
|
||||
// Reset to initialized state.
|
||||
void Context::reset()
|
||||
{
|
||||
std::for_each(mMacros.begin(), mMacros.end(), DeleteSecond());
|
||||
mMacros.clear();
|
||||
|
||||
delete mInput;
|
||||
mInput = NULL;
|
||||
|
||||
mOutput = NULL;
|
||||
}
|
||||
|
||||
void Context::defineBuiltInMacro(const std::string& name, int value)
|
||||
{
|
||||
std::ostringstream stream;
|
||||
stream << value;
|
||||
Token* token = new Token(0, INT_CONSTANT, new std::string(stream.str()));
|
||||
TokenVector* replacements = new pp::TokenVector(1, token);
|
||||
|
||||
mMacros[name] = new Macro(Macro::kTypeObj,
|
||||
new std::string(name),
|
||||
NULL,
|
||||
replacements);
|
||||
}
|
||||
|
||||
} // namespace pp
|
||||
|
||||
|
@ -7,6 +7,9 @@
|
||||
#ifndef COMPILER_PREPROCESSOR_CONTEXT_H_
|
||||
#define COMPILER_PREPROCESSOR_CONTEXT_H_
|
||||
|
||||
#include <map>
|
||||
|
||||
#include "common/angleutils.h"
|
||||
#include "Input.h"
|
||||
#include "Macro.h"
|
||||
#include "Token.h"
|
||||
@ -14,16 +17,42 @@
|
||||
namespace pp
|
||||
{
|
||||
|
||||
struct Context
|
||||
class Context
|
||||
{
|
||||
Context(int count, const char* const string[], const int length[],
|
||||
public:
|
||||
Context();
|
||||
~Context();
|
||||
|
||||
bool init();
|
||||
bool process(int count, const char* const string[], const int length[],
|
||||
TokenVector* output);
|
||||
|
||||
Input input;
|
||||
TokenVector* output;
|
||||
void* lexer() { return mLexer; }
|
||||
int readInput(char* buf, int maxSize);
|
||||
TokenVector* output() { return mOutput; }
|
||||
|
||||
void* lexer; // Lexer handle.
|
||||
MacroSet macros; // Defined macros.
|
||||
bool defineMacro(pp::Token::Location location,
|
||||
pp::Macro::Type type,
|
||||
std::string* name,
|
||||
pp::TokenVector* parameters,
|
||||
pp::TokenVector* replacements);
|
||||
bool undefineMacro(const std::string* name);
|
||||
bool isMacroDefined(const std::string* name);
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(Context);
|
||||
typedef std::map<std::string, Macro*> MacroSet;
|
||||
|
||||
void reset();
|
||||
bool initLexer();
|
||||
void destroyLexer();
|
||||
void defineBuiltInMacro(const std::string& name, int value);
|
||||
bool parse();
|
||||
|
||||
void* mLexer; // Lexer handle.
|
||||
Input* mInput;
|
||||
TokenVector* mOutput;
|
||||
MacroSet mMacros; // Defined macros.
|
||||
};
|
||||
|
||||
} // namespace pp
|
||||
|
@ -7,27 +7,44 @@
|
||||
#ifndef COMPILER_PREPROCESSOR_MACRO_H_
|
||||
#define COMPILER_PREPROCESSOR_MACRO_H_
|
||||
|
||||
#include <map>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include "common/angleutils.h"
|
||||
#include "Token.h"
|
||||
|
||||
namespace pp
|
||||
{
|
||||
|
||||
struct Macro
|
||||
class Macro
|
||||
{
|
||||
public:
|
||||
enum Type
|
||||
{
|
||||
kTypeObj,
|
||||
kTypeFunc
|
||||
};
|
||||
Type type;
|
||||
std::string identifier;
|
||||
TokenVector parameters;
|
||||
TokenVector replacements;
|
||||
|
||||
// Takes ownership of pointer parameters.
|
||||
Macro(Type type,
|
||||
std::string* name,
|
||||
TokenVector* parameters,
|
||||
TokenVector* replacements);
|
||||
~Macro();
|
||||
|
||||
Type type() const { return mType; }
|
||||
const std::string* identifier() const { return mName; }
|
||||
const TokenVector* parameters() const { return mParameters; }
|
||||
const TokenVector* replacements() const { return mReplacements; }
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(Macro);
|
||||
|
||||
Type mType;
|
||||
std::string* mName;
|
||||
TokenVector* mParameters;
|
||||
TokenVector* mReplacements;
|
||||
};
|
||||
typedef std::map<std::string, Macro> MacroSet;
|
||||
|
||||
} // namespace pp
|
||||
#endif COMPILER_PREPROCESSOR_MACRO_H_
|
||||
|
@ -6,12 +6,30 @@
|
||||
|
||||
#include "Preprocessor.h"
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
#include "compiler/debug.h"
|
||||
#include "Context.h"
|
||||
#include "stl_utils.h"
|
||||
|
||||
namespace pp
|
||||
{
|
||||
|
||||
Preprocessor::Preprocessor() : mContext(NULL)
|
||||
{
|
||||
}
|
||||
|
||||
Preprocessor::~Preprocessor()
|
||||
{
|
||||
delete mContext;
|
||||
}
|
||||
|
||||
bool Preprocessor::init()
|
||||
{
|
||||
mContext = new Context;
|
||||
return mContext->init();
|
||||
}
|
||||
|
||||
bool Preprocessor::process(int count,
|
||||
const char* const string[],
|
||||
const int length[])
|
||||
@ -20,22 +38,14 @@ bool Preprocessor::process(int count,
|
||||
if ((count < 0) || (string == NULL))
|
||||
return false;
|
||||
|
||||
clearResults();
|
||||
Context context(count, string, length, &mTokens);
|
||||
if (!initLexer(&context))
|
||||
return false;
|
||||
reset();
|
||||
|
||||
bool success = parse(&context);
|
||||
|
||||
destroyLexer(&context);
|
||||
return success;
|
||||
return mContext->process(count, string, length, &mTokens);
|
||||
}
|
||||
|
||||
void Preprocessor::clearResults()
|
||||
void Preprocessor::reset()
|
||||
{
|
||||
for (TokenVector::iterator i = mTokens.begin(); i != mTokens.end(); ++i)
|
||||
delete (*i);
|
||||
|
||||
std::for_each(mTokens.begin(), mTokens.end(), Delete());
|
||||
mTokens.clear();
|
||||
}
|
||||
|
||||
|
@ -13,27 +13,27 @@
|
||||
namespace pp
|
||||
{
|
||||
|
||||
struct Context;
|
||||
class Context;
|
||||
|
||||
class Preprocessor
|
||||
{
|
||||
public:
|
||||
Preprocessor() { }
|
||||
Preprocessor();
|
||||
~Preprocessor();
|
||||
|
||||
bool init();
|
||||
|
||||
bool process(int count, const char* const string[], const int length[]);
|
||||
|
||||
TokenIterator begin() const { return mTokens.begin(); }
|
||||
TokenIterator end() const { return mTokens.end(); }
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(Preprocessor);
|
||||
|
||||
static bool initLexer(Context* context);
|
||||
static void destroyLexer(Context* context);
|
||||
static bool parse(Context* context);
|
||||
|
||||
void clearResults();
|
||||
// Reset to initialized state.
|
||||
void reset();
|
||||
|
||||
Context* mContext;
|
||||
TokenVector mTokens; // Output.
|
||||
};
|
||||
|
||||
|
@ -40,9 +40,6 @@ std::ostream& operator<<(std::ostream& out, const Token& token)
|
||||
{
|
||||
switch (token.type())
|
||||
{
|
||||
case SPACE:
|
||||
out << " ";
|
||||
break;
|
||||
case INT_CONSTANT:
|
||||
case FLOAT_CONSTANT:
|
||||
case IDENTIFIER:
|
||||
|
@ -10,6 +10,8 @@
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include "common/angleutils.h"
|
||||
|
||||
namespace pp
|
||||
{
|
||||
|
||||
@ -29,6 +31,8 @@ class Token
|
||||
const std::string* value() const { return mValue; }
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(Token);
|
||||
|
||||
Location mLocation;
|
||||
int mType;
|
||||
std::string* mValue;
|
||||
|
@ -26,7 +26,6 @@ IF YOU MODIFY THIS FILE YOU ALSO NEED TO RUN generate_parser.sh.
|
||||
#include "compiler/debug.h"
|
||||
#include "Context.h"
|
||||
#include "pp_tab.h"
|
||||
#include "Preprocessor.h"
|
||||
|
||||
#define YY_USER_ACTION \
|
||||
do { \
|
||||
@ -36,9 +35,9 @@ IF YOU MODIFY THIS FILE YOU ALSO NEED TO RUN generate_parser.sh.
|
||||
} while(0);
|
||||
|
||||
#define YY_INPUT(buf, result, maxSize) \
|
||||
result = readInput(yyextra, buf, maxSize);
|
||||
result = yyextra->readInput(buf, maxSize);
|
||||
|
||||
static int readInput(pp::Context* context, char* buf, int maxSize);
|
||||
static std::string* extractMacroName(const char* str, int len);
|
||||
%}
|
||||
|
||||
%option noyywrap nounput never-interactive
|
||||
@ -64,9 +63,15 @@ FRACTIONAL_CONSTANT ({DIGIT}*"."{DIGIT}+)|({DIGIT}+".")
|
||||
|
||||
{HASH} { return HASH; }
|
||||
|
||||
{HASH}define { return HASH_DEFINE_OBJ; }
|
||||
{HASH}define{HSPACE}+/{IDENTIFIER}"(" { return HASH_DEFINE_FUNC; }
|
||||
{HASH}undef { return HASH_UNDEF; }
|
||||
{HASH}define{HSPACE}+{IDENTIFIER}/[ \t\n] {
|
||||
yylval->sval = extractMacroName(yytext, yyleng);
|
||||
return HASH_DEFINE_OBJ;
|
||||
}
|
||||
{HASH}define{HSPACE}+{IDENTIFIER}/"(" {
|
||||
yylval->sval = extractMacroName(yytext, yyleng);
|
||||
return HASH_DEFINE_FUNC;
|
||||
}
|
||||
{HASH}undef{HSPACE}+ { return HASH_UNDEF; }
|
||||
|
||||
{HASH}if { return HASH_IF; }
|
||||
{HASH}ifdef { return HASH_IFDEF; }
|
||||
@ -99,7 +104,7 @@ FRACTIONAL_CONSTANT ({DIGIT}*"."{DIGIT}+)|({DIGIT}+".")
|
||||
|
||||
{PUNCTUATOR} { return yytext[0]; }
|
||||
|
||||
{HSPACE}+ { return SPACE; }
|
||||
[ \t\v\f]+ { /* Ignore whitespace */ }
|
||||
|
||||
\n {
|
||||
++yylineno; yycolumn = 0;
|
||||
@ -110,24 +115,42 @@ FRACTIONAL_CONSTANT ({DIGIT}*"."{DIGIT}+)|({DIGIT}+".")
|
||||
|
||||
%%
|
||||
|
||||
int readInput(pp::Context* context, char* buf, int maxSize)
|
||||
std::string* extractMacroName(const char* str, int len)
|
||||
{
|
||||
yyscan_t lexer = context->lexer;
|
||||
ASSERT(lexer);
|
||||
// The input string is of the form {HASH}define{HSPACE}+{IDENTIFIER}
|
||||
// We just need to find the last HSPACE.
|
||||
ASSERT(str && (len > 8)); // strlen("#define ") == 8;
|
||||
|
||||
std::string* name = NULL;
|
||||
for (int i = len - 1; i >= 0; --i)
|
||||
{
|
||||
if ((str[i] == ' ') || (str[i] == '\t'))
|
||||
{
|
||||
name = new std::string(str + i + 1, len - i - 1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
ASSERT(name);
|
||||
return name;
|
||||
}
|
||||
|
||||
namespace pp {
|
||||
|
||||
int Context::readInput(char* buf, int maxSize)
|
||||
{
|
||||
int nread = YY_NULL;
|
||||
while (!context->input.eof() &&
|
||||
(context->input.error() == pp::Input::kErrorNone) &&
|
||||
while (!mInput->eof() &&
|
||||
(mInput->error() == pp::Input::kErrorNone) &&
|
||||
(nread == YY_NULL))
|
||||
{
|
||||
int line = 0, file = 0;
|
||||
pp::Token::decodeLocation(yyget_lineno(lexer), &line, &file);
|
||||
file = context->input.stringIndex();
|
||||
yyset_lineno(pp::Token::encodeLocation(line, file), lexer);
|
||||
pp::Token::decodeLocation(yyget_lineno(mLexer), &line, &file);
|
||||
file = mInput->stringIndex();
|
||||
yyset_lineno(pp::Token::encodeLocation(line, file), mLexer);
|
||||
|
||||
nread = context->input.read(buf, maxSize);
|
||||
nread = mInput->read(buf, maxSize);
|
||||
|
||||
if (context->input.error() == pp::Input::kErrorUnexpectedEOF)
|
||||
if (mInput->error() == pp::Input::kErrorUnexpectedEOF)
|
||||
{
|
||||
// TODO(alokp): Report error.
|
||||
}
|
||||
@ -135,27 +158,23 @@ int readInput(pp::Context* context, char* buf, int maxSize)
|
||||
return nread;
|
||||
}
|
||||
|
||||
namespace pp {
|
||||
|
||||
bool Preprocessor::initLexer(Context* context)
|
||||
bool Context::initLexer()
|
||||
{
|
||||
ASSERT(context->lexer == NULL);
|
||||
ASSERT(mLexer == NULL);
|
||||
|
||||
yyscan_t lexer = 0;
|
||||
if (yylex_init_extra(context, &lexer))
|
||||
if (yylex_init_extra(this, &mLexer))
|
||||
return false;
|
||||
|
||||
context->lexer = lexer;
|
||||
yyrestart(0, lexer);
|
||||
yyrestart(0, mLexer);
|
||||
return true;
|
||||
}
|
||||
|
||||
void Preprocessor::destroyLexer(Context* context)
|
||||
void Context::destroyLexer()
|
||||
{
|
||||
ASSERT(context->lexer);
|
||||
ASSERT(mLexer);
|
||||
|
||||
yylex_destroy(context->lexer);
|
||||
context->lexer = 0;
|
||||
yylex_destroy(mLexer);
|
||||
mLexer = NULL;
|
||||
}
|
||||
|
||||
} // namespace pp
|
||||
|
@ -23,9 +23,8 @@ WHICH GENERATES THE GLSL ES PARSER.
|
||||
// This file is auto-generated by generate_glslang_parser.sh. DO NOT EDIT!
|
||||
|
||||
#include "Context.h"
|
||||
#include "Preprocessor.h"
|
||||
|
||||
#define YYLEX_PARAM context->lexer
|
||||
#define YYLEX_PARAM context->lexer()
|
||||
#define YYDEBUG 1
|
||||
%}
|
||||
|
||||
@ -37,7 +36,6 @@ WHICH GENERATES THE GLSL ES PARSER.
|
||||
%union {
|
||||
int ival;
|
||||
std::string* sval;
|
||||
std::vector<std::string*>* slist;
|
||||
pp::Token* tval;
|
||||
pp::TokenVector* tlist;
|
||||
}
|
||||
@ -48,27 +46,18 @@ static void yyerror(YYLTYPE* llocp,
|
||||
pp::Context* context,
|
||||
const char* reason);
|
||||
|
||||
static void defineMacro(pp::Context* context,
|
||||
YYLTYPE* llocp,
|
||||
pp::Macro::Type type,
|
||||
const std::string* identifier,
|
||||
std::vector<std::string*>* parameters,
|
||||
pp::TokenVector* replacements);
|
||||
static void undefineMacro(pp::Context* context, const std::string* identifier);
|
||||
static bool isMacroDefined(pp::Context* context, const std::string* identifier);
|
||||
static void pushConditionalBlock(pp::Context* context, bool condition);
|
||||
static void popConditionalBlock(pp::Context* context);
|
||||
%}
|
||||
|
||||
%token HASH HASH_DEFINE_OBJ HASH_DEFINE_FUNC HASH_UNDEF
|
||||
%token HASH HASH_UNDEF
|
||||
%token HASH_IF HASH_IFDEF HASH_IFNDEF HASH_ELSE HASH_ELIF HASH_ENDIF DEFINED
|
||||
%token HASH_ERROR HASH_PRAGMA HASH_EXTENSION HASH_VERSION HASH_LINE
|
||||
%token SPACE
|
||||
%token <sval> HASH_DEFINE_OBJ HASH_DEFINE_FUNC
|
||||
%token <sval> INT_CONSTANT FLOAT_CONSTANT IDENTIFIER
|
||||
%type <ival> operator
|
||||
%type <slist> parameter_list
|
||||
%type <tval> conditional_token token
|
||||
%type <tlist> text_line replacement_token_list conditional_token_list token_list
|
||||
%type <tlist> parameter_list replacement_list conditional_list token_list
|
||||
%%
|
||||
|
||||
input
|
||||
@ -77,41 +66,41 @@ input
|
||||
;
|
||||
|
||||
line
|
||||
: text_line {
|
||||
// TODO(alokp): Expand macros.
|
||||
pp::TokenVector* out = context->output;
|
||||
out->insert(out->end(), $1->begin(), $1->end());
|
||||
delete $1;
|
||||
}
|
||||
: text_line
|
||||
| control_line
|
||||
;
|
||||
|
||||
text_line
|
||||
: '\n' { $$ = NULL; }
|
||||
| token_list '\n' { $$ = $1; }
|
||||
: '\n'
|
||||
| token_list '\n' {
|
||||
// TODO(alokp): Expand macros.
|
||||
pp::TokenVector* out = context->output();
|
||||
out->insert(out->end(), $1->begin(), $1->end());
|
||||
delete $1;
|
||||
}
|
||||
;
|
||||
|
||||
control_line
|
||||
: HASH '\n'
|
||||
| HASH_DEFINE_OBJ IDENTIFIER replacement_token_list '\n' {
|
||||
defineMacro(context, & @2, pp::Macro::kTypeObj, $2, NULL, $3);
|
||||
| HASH_DEFINE_OBJ replacement_list '\n' {
|
||||
context->defineMacro(@1.first_line, pp::Macro::kTypeObj, $1, NULL, $2);
|
||||
}
|
||||
| HASH_DEFINE_FUNC IDENTIFIER '(' parameter_list ')' replacement_token_list '\n' {
|
||||
defineMacro(context, & @2, pp::Macro::kTypeFunc, $2, $4, $6);
|
||||
| HASH_DEFINE_FUNC '(' parameter_list ')' replacement_list '\n' {
|
||||
context->defineMacro(@1.first_line, pp::Macro::kTypeFunc, $1, $3, $5);
|
||||
}
|
||||
| HASH_UNDEF IDENTIFIER '\n' {
|
||||
undefineMacro(context, $2);
|
||||
context->undefineMacro($2);
|
||||
}
|
||||
| HASH_IF conditional_token_list '\n' {
|
||||
| HASH_IF conditional_list '\n' {
|
||||
pushConditionalBlock(context, $2 ? true : false);
|
||||
}
|
||||
| HASH_IFDEF IDENTIFIER '\n' {
|
||||
pushConditionalBlock(context, isMacroDefined(context, $2));
|
||||
pushConditionalBlock(context, context->isMacroDefined($2));
|
||||
}
|
||||
| HASH_IFNDEF IDENTIFIER '\n' {
|
||||
pushConditionalBlock(context, !isMacroDefined(context, $2));
|
||||
pushConditionalBlock(context, !context->isMacroDefined($2));
|
||||
}
|
||||
| HASH_ELIF conditional_token_list '\n' {
|
||||
| HASH_ELIF conditional_list '\n' {
|
||||
}
|
||||
| HASH_ELSE '\n' {
|
||||
}
|
||||
@ -125,39 +114,29 @@ control_line
|
||||
| HASH_LINE '\n'
|
||||
;
|
||||
|
||||
replacement_token_list
|
||||
: /* empty */ { $$ = NULL }
|
||||
replacement_list
|
||||
: /* empty */ { $$ = NULL; }
|
||||
| token_list
|
||||
;
|
||||
|
||||
conditional_token_list
|
||||
: conditional_token {
|
||||
$$ = new pp::TokenVector;
|
||||
$$->push_back($1);
|
||||
}
|
||||
| conditional_token_list conditional_token {
|
||||
$$ = $1;
|
||||
$$->push_back($2);
|
||||
}
|
||||
;
|
||||
|
||||
conditional_token
|
||||
: DEFINED IDENTIFIER {
|
||||
}
|
||||
| DEFINED '(' IDENTIFIER ')' {
|
||||
}
|
||||
| token
|
||||
;
|
||||
|
||||
parameter_list
|
||||
: /* empty */ { $$ = NULL; }
|
||||
| IDENTIFIER {
|
||||
$$ = new std::vector<std::string*>();
|
||||
$$->push_back($1);
|
||||
$$ = new pp::TokenVector;
|
||||
$$->push_back(new pp::Token(@1.first_line, IDENTIFIER, $1));
|
||||
}
|
||||
| parameter_list ',' IDENTIFIER {
|
||||
$$ = $1;
|
||||
$$->push_back($3);
|
||||
$$->push_back(new pp::Token(@3.first_line, IDENTIFIER, $3));
|
||||
}
|
||||
|
||||
conditional_list
|
||||
: conditional_token {
|
||||
$$ = new pp::TokenVector;
|
||||
$$->push_back($1);
|
||||
}
|
||||
| conditional_list conditional_token {
|
||||
$$ = $1;
|
||||
$$->push_back($2);
|
||||
}
|
||||
;
|
||||
|
||||
@ -172,13 +151,18 @@ token_list
|
||||
}
|
||||
;
|
||||
|
||||
conditional_token
|
||||
: DEFINED IDENTIFIER {
|
||||
}
|
||||
| DEFINED '(' IDENTIFIER ')' {
|
||||
}
|
||||
| token
|
||||
;
|
||||
|
||||
token
|
||||
: operator {
|
||||
$$ = new pp::Token(@1.first_line, $1, NULL);
|
||||
}
|
||||
| SPACE {
|
||||
$$ = new pp::Token(@1.first_line, SPACE, NULL);
|
||||
}
|
||||
| INT_CONSTANT {
|
||||
$$ = new pp::Token(@1.first_line, INT_CONSTANT, $1);
|
||||
}
|
||||
@ -223,24 +207,6 @@ void yyerror(YYLTYPE* llocp, pp::Context* context, const char* reason)
|
||||
{
|
||||
}
|
||||
|
||||
void defineMacro(pp::Context* context,
|
||||
YYLTYPE* llocp,
|
||||
pp::Macro::Type type,
|
||||
const std::string* identifier,
|
||||
std::vector<std::string*>* parameters,
|
||||
pp::TokenVector* replacements)
|
||||
{
|
||||
}
|
||||
|
||||
void undefineMacro(pp::Context* context, const std::string* identifier)
|
||||
{
|
||||
}
|
||||
|
||||
bool isMacroDefined(pp::Context* context, const std::string* identifier)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
void pushConditionalBlock(pp::Context* context, bool condition)
|
||||
{
|
||||
}
|
||||
@ -250,10 +216,10 @@ void popConditionalBlock(pp::Context* context)
|
||||
}
|
||||
|
||||
namespace pp {
|
||||
bool Preprocessor::parse(Context* context)
|
||||
bool Context::parse()
|
||||
{
|
||||
yydebug = 1;
|
||||
return yyparse(context) == 0 ? true : false;
|
||||
return yyparse(this) == 0 ? true : false;
|
||||
}
|
||||
} // namespace pp
|
||||
|
||||
|
@ -380,48 +380,38 @@ struct yy_trans_info
|
||||
flex_int32_t yy_verify;
|
||||
flex_int32_t yy_nxt;
|
||||
};
|
||||
static yyconst flex_int16_t yy_acclist[57] =
|
||||
static yyconst flex_int16_t yy_accept[105] =
|
||||
{ 0,
|
||||
24, 23, 21, 23, 22, 23, 20, 23, 20, 23,
|
||||
18, 23, 18, 23, 17, 23, 17, 23, 21, 23,
|
||||
1, 23, 21, 19, 19, 18, 18, 17, 17, 21,
|
||||
1, 1, 19, 18, 17, 5, 19, 17, 17, 9,
|
||||
8, 16, 17, 10, 12, 6, 4, 11, 17, 2,
|
||||
7, 13,16387, 15, 8195, 14
|
||||
} ;
|
||||
0, 0, 24, 23, 21, 22, 20, 20, 18, 18,
|
||||
17, 17, 21, 1, 21, 19, 19, 18, 0, 0,
|
||||
0, 18, 17, 17, 21, 1, 1, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 19, 18, 17, 0,
|
||||
0, 0, 0, 0, 5, 0, 0, 0, 0, 0,
|
||||
19, 17, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 17, 0, 9, 8, 0, 0,
|
||||
0, 0, 0, 16, 0, 0, 0, 17, 0, 10,
|
||||
12, 0, 6, 0, 0, 0, 0, 11, 0, 0,
|
||||
7, 13, 4, 0, 0, 0, 15, 0, 0, 2,
|
||||
|
||||
static yyconst flex_int16_t yy_accept[104] =
|
||||
{ 0,
|
||||
1, 1, 1, 2, 3, 5, 7, 9, 11, 13,
|
||||
15, 17, 19, 21, 23, 24, 25, 26, 27, 27,
|
||||
27, 27, 28, 29, 30, 31, 32, 33, 33, 33,
|
||||
33, 33, 33, 33, 33, 33, 33, 34, 35, 36,
|
||||
36, 36, 36, 36, 36, 37, 37, 37, 37, 37,
|
||||
37, 38, 39, 39, 39, 39, 39, 39, 39, 39,
|
||||
39, 39, 39, 39, 39, 40, 40, 41, 42, 42,
|
||||
42, 42, 42, 42, 43, 43, 43, 43, 44, 44,
|
||||
45, 46, 46, 47, 47, 47, 48, 48, 50, 51,
|
||||
51, 52, 53, 53, 54, 54, 55, 55, 55, 56,
|
||||
|
||||
56, 57, 57
|
||||
3, 0, 14, 0
|
||||
} ;
|
||||
|
||||
static yyconst flex_int32_t yy_ec[256] =
|
||||
{ 0,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 2, 3,
|
||||
4, 4, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 2, 4, 1, 5, 1, 4, 4, 1, 6,
|
||||
4, 4, 7, 4, 7, 8, 4, 9, 10, 10,
|
||||
10, 10, 10, 10, 10, 11, 11, 4, 4, 4,
|
||||
4, 4, 4, 1, 12, 12, 12, 12, 13, 12,
|
||||
14, 14, 14, 14, 14, 14, 14, 14, 14, 14,
|
||||
14, 14, 14, 14, 14, 14, 14, 15, 14, 14,
|
||||
4, 1, 4, 4, 14, 1, 16, 12, 12, 17,
|
||||
1, 2, 5, 1, 6, 1, 5, 5, 1, 7,
|
||||
5, 5, 8, 5, 8, 9, 5, 10, 11, 11,
|
||||
11, 11, 11, 11, 11, 12, 12, 5, 5, 5,
|
||||
5, 5, 5, 1, 13, 13, 13, 13, 14, 13,
|
||||
15, 15, 15, 15, 15, 15, 15, 15, 15, 15,
|
||||
15, 15, 15, 15, 15, 15, 15, 16, 15, 15,
|
||||
5, 1, 5, 5, 15, 1, 17, 13, 13, 18,
|
||||
|
||||
18, 19, 20, 14, 21, 14, 14, 22, 23, 24,
|
||||
25, 26, 14, 27, 28, 29, 30, 31, 14, 32,
|
||||
14, 14, 4, 4, 4, 4, 1, 1, 1, 1,
|
||||
19, 20, 21, 15, 22, 15, 15, 23, 24, 25,
|
||||
26, 27, 15, 28, 29, 30, 31, 32, 15, 33,
|
||||
15, 15, 5, 5, 5, 5, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
@ -438,119 +428,112 @@ static yyconst flex_int32_t yy_ec[256] =
|
||||
1, 1, 1, 1, 1
|
||||
} ;
|
||||
|
||||
static yyconst flex_int32_t yy_meta[33] =
|
||||
static yyconst flex_int32_t yy_meta[34] =
|
||||
{ 0,
|
||||
1, 2, 1, 1, 1, 3, 1, 1, 4, 4,
|
||||
4, 5, 6, 7, 7, 5, 5, 6, 5, 7,
|
||||
1, 2, 3, 1, 1, 1, 3, 1, 1, 4,
|
||||
4, 4, 5, 6, 7, 7, 5, 5, 6, 5,
|
||||
7, 7, 7, 7, 7, 7, 7, 7, 7, 7,
|
||||
7, 7
|
||||
7, 7, 7
|
||||
} ;
|
||||
|
||||
static yyconst flex_int16_t yy_base[109] =
|
||||
static yyconst flex_int16_t yy_base[111] =
|
||||
{ 0,
|
||||
0, 17, 171, 172, 168, 172, 172, 3, 27, 52,
|
||||
0, 151, 27, 69, 166, 26, 28, 1, 21, 40,
|
||||
0, 0, 0, 148, 50, 0, 0, 148, 42, 146,
|
||||
143, 136, 138, 143, 47, 66, 69, 0, 139, 140,
|
||||
60, 141, 130, 127, 65, 131, 138, 136, 125, 74,
|
||||
83, 127, 129, 130, 130, 126, 121, 127, 126, 126,
|
||||
124, 121, 122, 111, 120, 113, 172, 172, 117, 108,
|
||||
110, 114, 114, 172, 108, 111, 108, 103, 101, 172,
|
||||
172, 85, 172, 79, 81, 172, 71, 0, 71, 51,
|
||||
172, 172, 44, 65, 28, 172, 42, 19, 172, 9,
|
||||
0, 18, 184, 185, 11, 185, 185, 21, 28, 53,
|
||||
0, 164, 39, 71, 12, 32, 34, 1, 39, 44,
|
||||
0, 0, 0, 162, 64, 0, 0, 162, 46, 160,
|
||||
157, 150, 152, 157, 70, 47, 65, 0, 153, 154,
|
||||
62, 155, 144, 141, 67, 145, 152, 150, 139, 76,
|
||||
85, 141, 143, 144, 144, 140, 135, 141, 140, 140,
|
||||
138, 135, 136, 125, 134, 127, 185, 185, 131, 122,
|
||||
124, 128, 128, 185, 122, 125, 122, 125, 123, 185,
|
||||
185, 112, 185, 120, 113, 127, 97, 0, 107, 86,
|
||||
185, 185, 105, 76, 81, 34, 185, 97, 10, 185,
|
||||
|
||||
172, 172, 100, 104, 108, 111, 116, 121
|
||||
185, 103, 185, 185, 110, 114, 118, 121, 126, 132
|
||||
} ;
|
||||
|
||||
static yyconst flex_int16_t yy_def[109] =
|
||||
static yyconst flex_int16_t yy_def[111] =
|
||||
{ 0,
|
||||
103, 103, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
104, 104, 102, 102, 102, 105, 105, 9, 18, 102,
|
||||
106, 10, 104, 104, 102, 14, 14, 102, 102, 102,
|
||||
102, 102, 102, 102, 102, 102, 102, 106, 104, 102,
|
||||
102, 102, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
102, 104, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
102, 102, 102, 102, 104, 102, 102, 102, 102, 102,
|
||||
102, 102, 102, 102, 102, 102, 102, 104, 102, 102,
|
||||
102, 102, 102, 102, 102, 102, 102, 104, 102, 102,
|
||||
102, 102, 102, 107, 102, 102, 108, 102, 102, 108,
|
||||
105, 105, 104, 104, 104, 104, 104, 104, 104, 104,
|
||||
106, 106, 104, 104, 104, 107, 107, 9, 18, 104,
|
||||
108, 10, 106, 106, 104, 14, 14, 104, 104, 104,
|
||||
104, 104, 104, 104, 104, 104, 104, 108, 106, 104,
|
||||
104, 104, 104, 104, 104, 104, 104, 104, 104, 104,
|
||||
104, 106, 104, 104, 104, 104, 104, 104, 104, 104,
|
||||
104, 104, 104, 104, 106, 104, 104, 104, 104, 104,
|
||||
104, 104, 104, 104, 104, 104, 104, 106, 104, 104,
|
||||
104, 104, 104, 104, 104, 104, 104, 106, 104, 104,
|
||||
104, 104, 104, 104, 109, 104, 104, 110, 104, 104,
|
||||
|
||||
102, 0, 102, 102, 102, 102, 102, 102
|
||||
104, 110, 104, 0, 104, 104, 104, 104, 104, 104
|
||||
} ;
|
||||
|
||||
static yyconst flex_int16_t yy_nxt[205] =
|
||||
static yyconst flex_int16_t yy_nxt[219] =
|
||||
{ 0,
|
||||
4, 5, 6, 7, 4, 7, 7, 8, 9, 10,
|
||||
10, 16, 16, 16, 99, 102, 12, 4, 13, 6,
|
||||
7, 14, 7, 7, 8, 9, 10, 10, 25, 19,
|
||||
19, 26, 102, 12, 17, 18, 18, 19, 35, 20,
|
||||
35, 21, 101, 35, 20, 35, 36, 99, 37, 37,
|
||||
37, 25, 98, 50, 26, 51, 51, 51, 21, 17,
|
||||
22, 22, 22, 41, 20, 42, 94, 96, 43, 20,
|
||||
27, 95, 94, 44, 37, 37, 37, 37, 37, 37,
|
||||
54, 59, 51, 51, 51, 28, 29, 55, 60, 30,
|
||||
31, 51, 51, 51, 32, 93, 92, 91, 33, 34,
|
||||
4, 5, 6, 5, 7, 4, 7, 7, 8, 9,
|
||||
10, 10, 15, 15, 15, 15, 104, 12, 4, 13,
|
||||
6, 5, 7, 14, 7, 7, 8, 9, 10, 10,
|
||||
16, 16, 16, 104, 103, 12, 17, 18, 18, 19,
|
||||
25, 20, 15, 21, 26, 35, 20, 35, 19, 19,
|
||||
35, 36, 35, 37, 37, 37, 37, 37, 37, 99,
|
||||
21, 17, 22, 22, 22, 25, 20, 15, 41, 26,
|
||||
42, 20, 27, 43, 37, 37, 37, 50, 44, 51,
|
||||
51, 51, 95, 54, 59, 51, 51, 51, 28, 29,
|
||||
55, 60, 30, 31, 51, 51, 51, 32, 100, 100,
|
||||
|
||||
97, 33, 34, 101, 100, 100, 93, 96, 95, 101,
|
||||
11, 11, 11, 11, 11, 11, 11, 23, 23, 23,
|
||||
23, 16, 90, 16, 38, 38, 38, 97, 89, 88,
|
||||
97, 97, 97, 100, 100, 100, 100, 100, 87, 86,
|
||||
85, 84, 83, 82, 81, 80, 79, 78, 77, 76,
|
||||
75, 74, 73, 72, 71, 70, 69, 68, 67, 66,
|
||||
65, 64, 63, 62, 61, 58, 57, 56, 53, 52,
|
||||
49, 48, 47, 46, 45, 40, 39, 15, 24, 15,
|
||||
102, 3, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
102, 102, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
102, 102, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
23, 16, 94, 16, 38, 38, 38, 98, 93, 92,
|
||||
98, 98, 98, 102, 102, 102, 102, 102, 102, 91,
|
||||
90, 89, 88, 87, 86, 85, 84, 83, 82, 81,
|
||||
80, 79, 78, 77, 76, 75, 74, 73, 72, 71,
|
||||
70, 69, 68, 67, 66, 65, 64, 63, 62, 61,
|
||||
58, 57, 56, 53, 52, 49, 48, 47, 46, 45,
|
||||
40, 39, 24, 104, 3, 104, 104, 104, 104, 104,
|
||||
104, 104, 104, 104, 104, 104, 104, 104, 104, 104,
|
||||
|
||||
102, 102, 102, 102
|
||||
104, 104, 104, 104, 104, 104, 104, 104, 104, 104,
|
||||
104, 104, 104, 104, 104, 104, 104, 104
|
||||
} ;
|
||||
|
||||
static yyconst flex_int16_t yy_chk[205] =
|
||||
static yyconst flex_int16_t yy_chk[219] =
|
||||
{ 0,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 8, 8, 8, 100, 18, 1, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 13, 19,
|
||||
19, 13, 18, 2, 9, 9, 9, 9, 16, 9,
|
||||
17, 9, 98, 16, 9, 17, 20, 97, 20, 20,
|
||||
20, 25, 95, 35, 25, 35, 35, 35, 9, 10,
|
||||
10, 10, 10, 29, 10, 29, 94, 93, 29, 10,
|
||||
14, 90, 89, 29, 36, 36, 36, 37, 37, 37,
|
||||
41, 45, 50, 50, 50, 14, 14, 41, 45, 14,
|
||||
14, 51, 51, 51, 14, 87, 85, 84, 14, 14,
|
||||
1, 1, 5, 15, 5, 15, 18, 1, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
8, 8, 8, 18, 99, 2, 9, 9, 9, 9,
|
||||
13, 9, 13, 9, 13, 16, 9, 17, 19, 19,
|
||||
16, 20, 17, 20, 20, 20, 36, 36, 36, 96,
|
||||
9, 10, 10, 10, 10, 25, 10, 25, 29, 25,
|
||||
29, 10, 14, 29, 37, 37, 37, 35, 29, 35,
|
||||
35, 35, 95, 41, 45, 50, 50, 50, 14, 14,
|
||||
41, 45, 14, 14, 51, 51, 51, 14, 98, 98,
|
||||
|
||||
103, 103, 103, 103, 103, 103, 103, 104, 104, 104,
|
||||
104, 105, 82, 105, 106, 106, 106, 107, 79, 78,
|
||||
107, 107, 107, 108, 108, 108, 108, 108, 77, 76,
|
||||
75, 73, 72, 71, 70, 69, 66, 65, 64, 63,
|
||||
62, 61, 60, 59, 58, 57, 56, 55, 54, 53,
|
||||
52, 49, 48, 47, 46, 44, 43, 42, 40, 39,
|
||||
34, 33, 32, 31, 30, 28, 24, 15, 12, 5,
|
||||
3, 102, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
102, 102, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
102, 102, 102, 102, 102, 102, 102, 102, 102, 102,
|
||||
94, 14, 14, 98, 102, 102, 93, 90, 89, 102,
|
||||
105, 105, 105, 105, 105, 105, 105, 106, 106, 106,
|
||||
106, 107, 87, 107, 108, 108, 108, 109, 86, 85,
|
||||
109, 109, 109, 110, 110, 110, 110, 110, 110, 84,
|
||||
82, 79, 78, 77, 76, 75, 73, 72, 71, 70,
|
||||
69, 66, 65, 64, 63, 62, 61, 60, 59, 58,
|
||||
57, 56, 55, 54, 53, 52, 49, 48, 47, 46,
|
||||
44, 43, 42, 40, 39, 34, 33, 32, 31, 30,
|
||||
28, 24, 12, 3, 104, 104, 104, 104, 104, 104,
|
||||
104, 104, 104, 104, 104, 104, 104, 104, 104, 104,
|
||||
|
||||
102, 102, 102, 102
|
||||
104, 104, 104, 104, 104, 104, 104, 104, 104, 104,
|
||||
104, 104, 104, 104, 104, 104, 104, 104
|
||||
} ;
|
||||
|
||||
/* Table of booleans, true if rule could match eol. */
|
||||
static yyconst flex_int32_t yy_rule_can_match_eol[24] =
|
||||
{ 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 1, 0, };
|
||||
|
||||
#define YY_TRAILING_MASK 0x2000
|
||||
#define YY_TRAILING_HEAD_MASK 0x4000
|
||||
#define REJECT \
|
||||
{ \
|
||||
*yy_cp = yyg->yy_hold_char; /* undo effects of setting up yytext */ \
|
||||
yy_cp = yyg->yy_full_match; /* restore poss. backed-over text */ \
|
||||
yyg->yy_lp = yyg->yy_full_lp; /* restore orig. accepting pos. */ \
|
||||
yyg->yy_state_ptr = yyg->yy_full_state; /* restore orig. state */ \
|
||||
yy_current_state = *yyg->yy_state_ptr; /* restore curr. state */ \
|
||||
++yyg->yy_lp; \
|
||||
goto find_rule; \
|
||||
}
|
||||
|
||||
/* The intent behind this definition is that it'll catch
|
||||
* any uses of REJECT which flex missed.
|
||||
*/
|
||||
#define REJECT reject_used_but_not_detected
|
||||
#define yymore() yymore_used_but_not_detected
|
||||
#define YY_MORE_ADJ 0
|
||||
#define YY_RESTORE_YY_MORE_OFFSET
|
||||
@ -571,7 +554,6 @@ IF YOU MODIFY THIS FILE YOU ALSO NEED TO RUN generate_parser.sh.
|
||||
#include "compiler/debug.h"
|
||||
#include "Context.h"
|
||||
#include "pp_tab.h"
|
||||
#include "Preprocessor.h"
|
||||
|
||||
#define YY_USER_ACTION \
|
||||
do { \
|
||||
@ -581,9 +563,9 @@ IF YOU MODIFY THIS FILE YOU ALSO NEED TO RUN generate_parser.sh.
|
||||
} while(0);
|
||||
|
||||
#define YY_INPUT(buf, result, maxSize) \
|
||||
result = readInput(yyextra, buf, maxSize);
|
||||
result = yyextra->readInput(buf, maxSize);
|
||||
|
||||
static int readInput(pp::Context* context, char* buf, int maxSize);
|
||||
static std::string* extractMacroName(const char* str, int len);
|
||||
|
||||
#define INITIAL 0
|
||||
|
||||
@ -617,17 +599,6 @@ struct yyguts_t
|
||||
int yylineno_r;
|
||||
int yy_flex_debug_r;
|
||||
|
||||
yy_state_type *yy_state_buf;
|
||||
yy_state_type *yy_state_ptr;
|
||||
char *yy_full_match;
|
||||
int yy_lp;
|
||||
|
||||
/* These are only needed for trailing context rules,
|
||||
* but there's no conditional variable for that yet. */
|
||||
int yy_looking_for_trail_begin;
|
||||
int yy_full_lp;
|
||||
int *yy_full_state;
|
||||
|
||||
char *yytext_r;
|
||||
int yy_more_flag;
|
||||
int yy_more_len;
|
||||
@ -844,12 +815,6 @@ YY_DECL
|
||||
YY_USER_INIT;
|
||||
#endif
|
||||
|
||||
/* Create the reject buffer large enough to save one state per allowed character. */
|
||||
if ( ! yyg->yy_state_buf )
|
||||
yyg->yy_state_buf = (yy_state_type *)ppalloc(YY_STATE_BUF_SIZE ,yyscanner);
|
||||
if ( ! yyg->yy_state_buf )
|
||||
YY_FATAL_ERROR( "out of dynamic memory in pplex()" );
|
||||
|
||||
if ( ! yyg->yy_start )
|
||||
yyg->yy_start = 1; /* first start state */
|
||||
|
||||
@ -882,64 +847,30 @@ YY_DECL
|
||||
|
||||
yy_current_state = yyg->yy_start;
|
||||
yy_current_state += YY_AT_BOL();
|
||||
|
||||
yyg->yy_state_ptr = yyg->yy_state_buf;
|
||||
*yyg->yy_state_ptr++ = yy_current_state;
|
||||
|
||||
yy_match:
|
||||
do
|
||||
{
|
||||
register YY_CHAR yy_c = yy_ec[YY_SC_TO_UI(*yy_cp)];
|
||||
if ( yy_accept[yy_current_state] )
|
||||
{
|
||||
yyg->yy_last_accepting_state = yy_current_state;
|
||||
yyg->yy_last_accepting_cpos = yy_cp;
|
||||
}
|
||||
while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
|
||||
{
|
||||
yy_current_state = (int) yy_def[yy_current_state];
|
||||
if ( yy_current_state >= 103 )
|
||||
if ( yy_current_state >= 105 )
|
||||
yy_c = yy_meta[(unsigned int) yy_c];
|
||||
}
|
||||
yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
|
||||
*yyg->yy_state_ptr++ = yy_current_state;
|
||||
++yy_cp;
|
||||
}
|
||||
while ( yy_current_state != 102 );
|
||||
while ( yy_current_state != 104 );
|
||||
yy_cp = yyg->yy_last_accepting_cpos;
|
||||
yy_current_state = yyg->yy_last_accepting_state;
|
||||
|
||||
yy_find_action:
|
||||
yy_current_state = *--yyg->yy_state_ptr;
|
||||
yyg->yy_lp = yy_accept[yy_current_state];
|
||||
find_rule: /* we branch to this label when backing up */
|
||||
for ( ; ; ) /* until we find what rule we matched */
|
||||
{
|
||||
if ( yyg->yy_lp && yyg->yy_lp < yy_accept[yy_current_state + 1] )
|
||||
{
|
||||
yy_act = yy_acclist[yyg->yy_lp];
|
||||
if ( yy_act & YY_TRAILING_HEAD_MASK ||
|
||||
yyg->yy_looking_for_trail_begin )
|
||||
{
|
||||
if ( yy_act == yyg->yy_looking_for_trail_begin )
|
||||
{
|
||||
yyg->yy_looking_for_trail_begin = 0;
|
||||
yy_act &= ~YY_TRAILING_HEAD_MASK;
|
||||
break;
|
||||
}
|
||||
}
|
||||
else if ( yy_act & YY_TRAILING_MASK )
|
||||
{
|
||||
yyg->yy_looking_for_trail_begin = yy_act & ~YY_TRAILING_MASK;
|
||||
yyg->yy_looking_for_trail_begin |= YY_TRAILING_HEAD_MASK;
|
||||
}
|
||||
else
|
||||
{
|
||||
yyg->yy_full_match = yy_cp;
|
||||
yyg->yy_full_state = yyg->yy_state_ptr;
|
||||
yyg->yy_full_lp = yyg->yy_lp;
|
||||
break;
|
||||
}
|
||||
++yyg->yy_lp;
|
||||
goto find_rule;
|
||||
}
|
||||
--yy_cp;
|
||||
yy_current_state = *--yyg->yy_state_ptr;
|
||||
yyg->yy_lp = yy_accept[yy_current_state];
|
||||
}
|
||||
yy_act = yy_accept[yy_current_state];
|
||||
|
||||
YY_DO_BEFORE_ACTION;
|
||||
|
||||
@ -959,17 +890,37 @@ do_action: /* This label is used only to access EOF actions. */
|
||||
|
||||
switch ( yy_act )
|
||||
{ /* beginning of action switch */
|
||||
case 0: /* must back up */
|
||||
/* undo the effects of YY_DO_BEFORE_ACTION */
|
||||
*yy_cp = yyg->yy_hold_char;
|
||||
yy_cp = yyg->yy_last_accepting_cpos;
|
||||
yy_current_state = yyg->yy_last_accepting_state;
|
||||
goto yy_find_action;
|
||||
|
||||
case 1:
|
||||
YY_RULE_SETUP
|
||||
{ return HASH; }
|
||||
YY_BREAK
|
||||
case 2:
|
||||
/* rule 2 can match eol */
|
||||
*yy_cp = yyg->yy_hold_char; /* undo effects of setting up yytext */
|
||||
yyg->yy_c_buf_p = yy_cp -= 1;
|
||||
YY_DO_BEFORE_ACTION; /* set up yytext again */
|
||||
YY_RULE_SETUP
|
||||
{ return HASH_DEFINE_OBJ; }
|
||||
{
|
||||
yylval->sval = extractMacroName(yytext, yyleng);
|
||||
return HASH_DEFINE_OBJ;
|
||||
}
|
||||
YY_BREAK
|
||||
case 3:
|
||||
*yy_cp = yyg->yy_hold_char; /* undo effects of setting up yytext */
|
||||
yyg->yy_c_buf_p = yy_cp -= 1;
|
||||
YY_DO_BEFORE_ACTION; /* set up yytext again */
|
||||
YY_RULE_SETUP
|
||||
{ return HASH_DEFINE_FUNC; }
|
||||
{
|
||||
yylval->sval = extractMacroName(yytext, yyleng);
|
||||
return HASH_DEFINE_FUNC;
|
||||
}
|
||||
YY_BREAK
|
||||
case 4:
|
||||
YY_RULE_SETUP
|
||||
@ -1050,7 +1001,7 @@ YY_RULE_SETUP
|
||||
YY_BREAK
|
||||
case 21:
|
||||
YY_RULE_SETUP
|
||||
{ return SPACE; }
|
||||
{ /* Ignore whitespace */ }
|
||||
YY_BREAK
|
||||
case 22:
|
||||
/* rule 22 can match eol */
|
||||
@ -1131,7 +1082,8 @@ ECHO;
|
||||
|
||||
else
|
||||
{
|
||||
yy_cp = yyg->yy_c_buf_p;
|
||||
yy_cp = yyg->yy_last_accepting_cpos;
|
||||
yy_current_state = yyg->yy_last_accepting_state;
|
||||
goto yy_find_action;
|
||||
}
|
||||
}
|
||||
@ -1257,8 +1209,37 @@ static int yy_get_next_buffer (yyscan_t yyscanner)
|
||||
while ( num_to_read <= 0 )
|
||||
{ /* Not enough room in the buffer - grow it. */
|
||||
|
||||
/* just a shorter name for the current buffer */
|
||||
YY_BUFFER_STATE b = YY_CURRENT_BUFFER;
|
||||
|
||||
int yy_c_buf_p_offset =
|
||||
(int) (yyg->yy_c_buf_p - b->yy_ch_buf);
|
||||
|
||||
if ( b->yy_is_our_buffer )
|
||||
{
|
||||
int new_size = b->yy_buf_size * 2;
|
||||
|
||||
if ( new_size <= 0 )
|
||||
b->yy_buf_size += b->yy_buf_size / 8;
|
||||
else
|
||||
b->yy_buf_size *= 2;
|
||||
|
||||
b->yy_ch_buf = (char *)
|
||||
/* Include room in for 2 EOB chars. */
|
||||
pprealloc((void *) b->yy_ch_buf,b->yy_buf_size + 2 ,yyscanner );
|
||||
}
|
||||
else
|
||||
/* Can't grow it, we don't own it. */
|
||||
b->yy_ch_buf = 0;
|
||||
|
||||
if ( ! b->yy_ch_buf )
|
||||
YY_FATAL_ERROR(
|
||||
"input buffer overflow, can't enlarge buffer because scanner uses REJECT" );
|
||||
"fatal error - scanner input buffer overflow" );
|
||||
|
||||
yyg->yy_c_buf_p = &b->yy_ch_buf[yy_c_buf_p_offset];
|
||||
|
||||
num_to_read = YY_CURRENT_BUFFER_LVALUE->yy_buf_size -
|
||||
number_to_move - 1;
|
||||
|
||||
}
|
||||
|
||||
@ -1319,20 +1300,21 @@ static int yy_get_next_buffer (yyscan_t yyscanner)
|
||||
yy_current_state = yyg->yy_start;
|
||||
yy_current_state += YY_AT_BOL();
|
||||
|
||||
yyg->yy_state_ptr = yyg->yy_state_buf;
|
||||
*yyg->yy_state_ptr++ = yy_current_state;
|
||||
|
||||
for ( yy_cp = yyg->yytext_ptr + YY_MORE_ADJ; yy_cp < yyg->yy_c_buf_p; ++yy_cp )
|
||||
{
|
||||
register YY_CHAR yy_c = (*yy_cp ? yy_ec[YY_SC_TO_UI(*yy_cp)] : 1);
|
||||
if ( yy_accept[yy_current_state] )
|
||||
{
|
||||
yyg->yy_last_accepting_state = yy_current_state;
|
||||
yyg->yy_last_accepting_cpos = yy_cp;
|
||||
}
|
||||
while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
|
||||
{
|
||||
yy_current_state = (int) yy_def[yy_current_state];
|
||||
if ( yy_current_state >= 103 )
|
||||
if ( yy_current_state >= 105 )
|
||||
yy_c = yy_meta[(unsigned int) yy_c];
|
||||
}
|
||||
yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
|
||||
*yyg->yy_state_ptr++ = yy_current_state;
|
||||
}
|
||||
|
||||
return yy_current_state;
|
||||
@ -1347,18 +1329,22 @@ static int yy_get_next_buffer (yyscan_t yyscanner)
|
||||
{
|
||||
register int yy_is_jam;
|
||||
struct yyguts_t * yyg = (struct yyguts_t*)yyscanner; /* This var may be unused depending upon options. */
|
||||
register char *yy_cp = yyg->yy_c_buf_p;
|
||||
|
||||
register YY_CHAR yy_c = 1;
|
||||
if ( yy_accept[yy_current_state] )
|
||||
{
|
||||
yyg->yy_last_accepting_state = yy_current_state;
|
||||
yyg->yy_last_accepting_cpos = yy_cp;
|
||||
}
|
||||
while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
|
||||
{
|
||||
yy_current_state = (int) yy_def[yy_current_state];
|
||||
if ( yy_current_state >= 103 )
|
||||
if ( yy_current_state >= 105 )
|
||||
yy_c = yy_meta[(unsigned int) yy_c];
|
||||
}
|
||||
yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
|
||||
yy_is_jam = (yy_current_state == 102);
|
||||
if ( ! yy_is_jam )
|
||||
*yyg->yy_state_ptr++ = yy_current_state;
|
||||
yy_is_jam = (yy_current_state == 104);
|
||||
|
||||
return yy_is_jam ? 0 : yy_current_state;
|
||||
}
|
||||
@ -2123,11 +2109,6 @@ static int yy_init_globals (yyscan_t yyscanner)
|
||||
yyg->yy_start_stack_depth = 0;
|
||||
yyg->yy_start_stack = NULL;
|
||||
|
||||
yyg->yy_state_buf = 0;
|
||||
yyg->yy_state_ptr = 0;
|
||||
yyg->yy_full_match = 0;
|
||||
yyg->yy_lp = 0;
|
||||
|
||||
/* Defined in main.c */
|
||||
#ifdef YY_STDINIT
|
||||
yyin = stdin;
|
||||
@ -2163,9 +2144,6 @@ int pplex_destroy (yyscan_t yyscanner)
|
||||
ppfree(yyg->yy_start_stack ,yyscanner );
|
||||
yyg->yy_start_stack = NULL;
|
||||
|
||||
ppfree ( yyg->yy_state_buf , yyscanner);
|
||||
yyg->yy_state_buf = NULL;
|
||||
|
||||
/* Reset the globals. This is important in a non-reentrant scanner so the next time
|
||||
* pplex() is called, initialization will occur. */
|
||||
yy_init_globals( yyscanner);
|
||||
@ -2224,24 +2202,42 @@ void ppfree (void * ptr , yyscan_t yyscanner)
|
||||
|
||||
#define YYTABLES_NAME "yytables"
|
||||
|
||||
int readInput(pp::Context* context, char* buf, int maxSize)
|
||||
std::string* extractMacroName(const char* str, int len)
|
||||
{
|
||||
yyscan_t lexer = context->lexer;
|
||||
ASSERT(lexer);
|
||||
// The input string is of the form {HASH}define{HSPACE}+{IDENTIFIER}
|
||||
// We just need to find the last HSPACE.
|
||||
ASSERT(str && (len > 8)); // strlen("#define ") == 8;
|
||||
|
||||
std::string* name = NULL;
|
||||
for (int i = len - 1; i >= 0; --i)
|
||||
{
|
||||
if ((str[i] == ' ') || (str[i] == '\t'))
|
||||
{
|
||||
name = new std::string(str + i + 1, len - i - 1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
ASSERT(name);
|
||||
return name;
|
||||
}
|
||||
|
||||
namespace pp {
|
||||
|
||||
int Context::readInput(char* buf, int maxSize)
|
||||
{
|
||||
int nread = YY_NULL;
|
||||
while (!context->input.eof() &&
|
||||
(context->input.error() == pp::Input::kErrorNone) &&
|
||||
while (!mInput->eof() &&
|
||||
(mInput->error() == pp::Input::kErrorNone) &&
|
||||
(nread == YY_NULL))
|
||||
{
|
||||
int line = 0, file = 0;
|
||||
pp::Token::decodeLocation(ppget_lineno(lexer), &line, &file);
|
||||
file = context->input.stringIndex();
|
||||
ppset_lineno(pp::Token::encodeLocation(line, file),lexer);
|
||||
pp::Token::decodeLocation(ppget_lineno(mLexer), &line, &file);
|
||||
file = mInput->stringIndex();
|
||||
ppset_lineno(pp::Token::encodeLocation(line, file),mLexer);
|
||||
|
||||
nread = context->input.read(buf, maxSize);
|
||||
nread = mInput->read(buf, maxSize);
|
||||
|
||||
if (context->input.error() == pp::Input::kErrorUnexpectedEOF)
|
||||
if (mInput->error() == pp::Input::kErrorUnexpectedEOF)
|
||||
{
|
||||
// TODO(alokp): Report error.
|
||||
}
|
||||
@ -2249,27 +2245,23 @@ int readInput(pp::Context* context, char* buf, int maxSize)
|
||||
return nread;
|
||||
}
|
||||
|
||||
namespace pp {
|
||||
|
||||
bool Preprocessor::initLexer(Context* context)
|
||||
bool Context::initLexer()
|
||||
{
|
||||
ASSERT(context->lexer == NULL);
|
||||
ASSERT(mLexer == NULL);
|
||||
|
||||
yyscan_t lexer = 0;
|
||||
if (pplex_init_extra(context,&lexer))
|
||||
if (pplex_init_extra(this,&mLexer))
|
||||
return false;
|
||||
|
||||
context->lexer = lexer;
|
||||
pprestart(0,lexer);
|
||||
pprestart(0,mLexer);
|
||||
return true;
|
||||
}
|
||||
|
||||
void Preprocessor::destroyLexer(Context* context)
|
||||
void Context::destroyLexer()
|
||||
{
|
||||
ASSERT(context->lexer);
|
||||
ASSERT(mLexer);
|
||||
|
||||
pplex_destroy(context->lexer);
|
||||
context->lexer = 0;
|
||||
pplex_destroy(mLexer);
|
||||
mLexer = NULL;
|
||||
}
|
||||
|
||||
} // namespace pp
|
||||
|
@ -75,48 +75,46 @@
|
||||
know about them. */
|
||||
enum yytokentype {
|
||||
HASH = 258,
|
||||
HASH_DEFINE_OBJ = 259,
|
||||
HASH_DEFINE_FUNC = 260,
|
||||
HASH_UNDEF = 261,
|
||||
HASH_IF = 262,
|
||||
HASH_IFDEF = 263,
|
||||
HASH_IFNDEF = 264,
|
||||
HASH_ELSE = 265,
|
||||
HASH_ELIF = 266,
|
||||
HASH_ENDIF = 267,
|
||||
DEFINED = 268,
|
||||
HASH_ERROR = 269,
|
||||
HASH_PRAGMA = 270,
|
||||
HASH_EXTENSION = 271,
|
||||
HASH_VERSION = 272,
|
||||
HASH_LINE = 273,
|
||||
SPACE = 274,
|
||||
INT_CONSTANT = 275,
|
||||
FLOAT_CONSTANT = 276,
|
||||
IDENTIFIER = 277
|
||||
HASH_UNDEF = 259,
|
||||
HASH_IF = 260,
|
||||
HASH_IFDEF = 261,
|
||||
HASH_IFNDEF = 262,
|
||||
HASH_ELSE = 263,
|
||||
HASH_ELIF = 264,
|
||||
HASH_ENDIF = 265,
|
||||
DEFINED = 266,
|
||||
HASH_ERROR = 267,
|
||||
HASH_PRAGMA = 268,
|
||||
HASH_EXTENSION = 269,
|
||||
HASH_VERSION = 270,
|
||||
HASH_LINE = 271,
|
||||
HASH_DEFINE_OBJ = 272,
|
||||
HASH_DEFINE_FUNC = 273,
|
||||
INT_CONSTANT = 274,
|
||||
FLOAT_CONSTANT = 275,
|
||||
IDENTIFIER = 276
|
||||
};
|
||||
#endif
|
||||
/* Tokens. */
|
||||
#define HASH 258
|
||||
#define HASH_DEFINE_OBJ 259
|
||||
#define HASH_DEFINE_FUNC 260
|
||||
#define HASH_UNDEF 261
|
||||
#define HASH_IF 262
|
||||
#define HASH_IFDEF 263
|
||||
#define HASH_IFNDEF 264
|
||||
#define HASH_ELSE 265
|
||||
#define HASH_ELIF 266
|
||||
#define HASH_ENDIF 267
|
||||
#define DEFINED 268
|
||||
#define HASH_ERROR 269
|
||||
#define HASH_PRAGMA 270
|
||||
#define HASH_EXTENSION 271
|
||||
#define HASH_VERSION 272
|
||||
#define HASH_LINE 273
|
||||
#define SPACE 274
|
||||
#define INT_CONSTANT 275
|
||||
#define FLOAT_CONSTANT 276
|
||||
#define IDENTIFIER 277
|
||||
#define HASH_UNDEF 259
|
||||
#define HASH_IF 260
|
||||
#define HASH_IFDEF 261
|
||||
#define HASH_IFNDEF 262
|
||||
#define HASH_ELSE 263
|
||||
#define HASH_ELIF 264
|
||||
#define HASH_ENDIF 265
|
||||
#define DEFINED 266
|
||||
#define HASH_ERROR 267
|
||||
#define HASH_PRAGMA 268
|
||||
#define HASH_EXTENSION 269
|
||||
#define HASH_VERSION 270
|
||||
#define HASH_LINE 271
|
||||
#define HASH_DEFINE_OBJ 272
|
||||
#define HASH_DEFINE_FUNC 273
|
||||
#define INT_CONSTANT 274
|
||||
#define FLOAT_CONSTANT 275
|
||||
#define IDENTIFIER 276
|
||||
|
||||
|
||||
|
||||
@ -133,9 +131,8 @@
|
||||
// This file is auto-generated by generate_glslang_parser.sh. DO NOT EDIT!
|
||||
|
||||
#include "Context.h"
|
||||
#include "Preprocessor.h"
|
||||
|
||||
#define YYLEX_PARAM context->lexer
|
||||
#define YYLEX_PARAM context->lexer()
|
||||
#define YYDEBUG 1
|
||||
|
||||
|
||||
@ -163,7 +160,6 @@ typedef union YYSTYPE
|
||||
{
|
||||
int ival;
|
||||
std::string* sval;
|
||||
std::vector<std::string*>* slist;
|
||||
pp::Token* tval;
|
||||
pp::TokenVector* tlist;
|
||||
}
|
||||
@ -197,14 +193,6 @@ static void yyerror(YYLTYPE* llocp,
|
||||
pp::Context* context,
|
||||
const char* reason);
|
||||
|
||||
static void defineMacro(pp::Context* context,
|
||||
YYLTYPE* llocp,
|
||||
pp::Macro::Type type,
|
||||
const std::string* identifier,
|
||||
std::vector<std::string*>* parameters,
|
||||
pp::TokenVector* replacements);
|
||||
static void undefineMacro(pp::Context* context, const std::string* identifier);
|
||||
static bool isMacroDefined(pp::Context* context, const std::string* identifier);
|
||||
static void pushConditionalBlock(pp::Context* context, bool condition);
|
||||
static void popConditionalBlock(pp::Context* context);
|
||||
|
||||
@ -427,20 +415,20 @@ union yyalloc
|
||||
/* YYFINAL -- State number of the termination state. */
|
||||
#define YYFINAL 2
|
||||
/* YYLAST -- Last index in YYTABLE. */
|
||||
#define YYLAST 244
|
||||
#define YYLAST 247
|
||||
|
||||
/* YYNTOKENS -- Number of terminals. */
|
||||
#define YYNTOKENS 48
|
||||
#define YYNTOKENS 47
|
||||
/* YYNNTS -- Number of nonterminals. */
|
||||
#define YYNNTS 12
|
||||
/* YYNRULES -- Number of rules. */
|
||||
#define YYNRULES 63
|
||||
#define YYNRULES 62
|
||||
/* YYNRULES -- Number of states. */
|
||||
#define YYNSTATES 94
|
||||
#define YYNSTATES 91
|
||||
|
||||
/* YYTRANSLATE(YYLEX) -- Bison symbol number corresponding to YYLEX. */
|
||||
#define YYUNDEFTOK 2
|
||||
#define YYMAXUTOK 277
|
||||
#define YYMAXUTOK 276
|
||||
|
||||
#define YYTRANSLATE(YYX) \
|
||||
((unsigned int) (YYX) <= YYMAXUTOK ? yytranslate[YYX] : YYUNDEFTOK)
|
||||
@ -449,18 +437,18 @@ union yyalloc
|
||||
static const yytype_uint8 yytranslate[] =
|
||||
{
|
||||
0, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
23, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
22, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 44, 2, 2, 2, 38, 41, 2,
|
||||
24, 25, 37, 34, 26, 35, 33, 36, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 45, 46,
|
||||
29, 43, 30, 47, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 43, 2, 2, 2, 37, 40, 2,
|
||||
23, 24, 36, 33, 25, 34, 32, 35, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 44, 45,
|
||||
28, 42, 29, 46, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 27, 2, 28, 39, 2, 2, 2, 2, 2,
|
||||
2, 26, 2, 27, 38, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 31, 40, 32, 42, 2, 2, 2,
|
||||
2, 2, 2, 30, 39, 31, 41, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
@ -475,7 +463,7 @@ static const yytype_uint8 yytranslate[] =
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
|
||||
2, 2, 2, 2, 2, 2, 1, 2, 3, 4,
|
||||
5, 6, 7, 8, 9, 10, 11, 12, 13, 14,
|
||||
15, 16, 17, 18, 19, 20, 21, 22
|
||||
15, 16, 17, 18, 19, 20, 21
|
||||
};
|
||||
|
||||
#if YYDEBUG
|
||||
@ -484,46 +472,45 @@ static const yytype_uint8 yytranslate[] =
|
||||
static const yytype_uint8 yyprhs[] =
|
||||
{
|
||||
0, 0, 3, 4, 7, 9, 11, 13, 16, 19,
|
||||
24, 32, 36, 40, 44, 48, 52, 55, 58, 61,
|
||||
64, 67, 70, 73, 74, 76, 78, 81, 84, 89,
|
||||
91, 92, 94, 98, 100, 103, 105, 107, 109, 111,
|
||||
113, 115, 117, 119, 121, 123, 125, 127, 129, 131,
|
||||
133, 135, 137, 139, 141, 143, 145, 147, 149, 151,
|
||||
153, 155, 157, 159
|
||||
23, 30, 34, 38, 42, 46, 50, 53, 56, 59,
|
||||
62, 65, 68, 71, 72, 74, 75, 77, 81, 83,
|
||||
86, 88, 91, 94, 99, 101, 103, 105, 107, 109,
|
||||
111, 113, 115, 117, 119, 121, 123, 125, 127, 129,
|
||||
131, 133, 135, 137, 139, 141, 143, 145, 147, 149,
|
||||
151, 153, 155
|
||||
};
|
||||
|
||||
/* YYRHS -- A `-1'-separated list of the rules' RHS. */
|
||||
static const yytype_int8 yyrhs[] =
|
||||
{
|
||||
49, 0, -1, -1, 49, 50, -1, 51, -1, 52,
|
||||
-1, 23, -1, 57, 23, -1, 3, 23, -1, 4,
|
||||
22, 53, 23, -1, 5, 22, 24, 56, 25, 53,
|
||||
23, -1, 6, 22, 23, -1, 7, 54, 23, -1,
|
||||
8, 22, 23, -1, 9, 22, 23, -1, 11, 54,
|
||||
23, -1, 10, 23, -1, 12, 23, -1, 14, 23,
|
||||
-1, 15, 23, -1, 16, 23, -1, 17, 23, -1,
|
||||
18, 23, -1, -1, 57, -1, 55, -1, 54, 55,
|
||||
-1, 13, 22, -1, 13, 24, 22, 25, -1, 58,
|
||||
-1, -1, 22, -1, 56, 26, 22, -1, 58, -1,
|
||||
57, 58, -1, 59, -1, 19, -1, 20, -1, 21,
|
||||
-1, 22, -1, 27, -1, 28, -1, 29, -1, 30,
|
||||
-1, 24, -1, 25, -1, 31, -1, 32, -1, 33,
|
||||
-1, 34, -1, 35, -1, 36, -1, 37, -1, 38,
|
||||
-1, 39, -1, 40, -1, 41, -1, 42, -1, 43,
|
||||
-1, 44, -1, 45, -1, 46, -1, 26, -1, 47,
|
||||
-1
|
||||
48, 0, -1, -1, 48, 49, -1, 50, -1, 51,
|
||||
-1, 22, -1, 55, 22, -1, 3, 22, -1, 17,
|
||||
52, 22, -1, 18, 23, 53, 24, 52, 22, -1,
|
||||
4, 21, 22, -1, 5, 54, 22, -1, 6, 21,
|
||||
22, -1, 7, 21, 22, -1, 9, 54, 22, -1,
|
||||
8, 22, -1, 10, 22, -1, 12, 22, -1, 13,
|
||||
22, -1, 14, 22, -1, 15, 22, -1, 16, 22,
|
||||
-1, -1, 55, -1, -1, 21, -1, 53, 25, 21,
|
||||
-1, 56, -1, 54, 56, -1, 57, -1, 55, 57,
|
||||
-1, 11, 21, -1, 11, 23, 21, 24, -1, 57,
|
||||
-1, 58, -1, 19, -1, 20, -1, 21, -1, 26,
|
||||
-1, 27, -1, 28, -1, 29, -1, 23, -1, 24,
|
||||
-1, 30, -1, 31, -1, 32, -1, 33, -1, 34,
|
||||
-1, 35, -1, 36, -1, 37, -1, 38, -1, 39,
|
||||
-1, 40, -1, 41, -1, 42, -1, 43, -1, 44,
|
||||
-1, 45, -1, 25, -1, 46, -1
|
||||
};
|
||||
|
||||
/* YYRLINE[YYN] -- source line where rule number YYN was defined. */
|
||||
static const yytype_uint8 yyrline[] =
|
||||
{
|
||||
0, 74, 74, 76, 80, 86, 90, 91, 95, 96,
|
||||
99, 102, 105, 108, 111, 114, 116, 118, 121, 122,
|
||||
123, 124, 125, 129, 130, 134, 138, 145, 147, 149,
|
||||
153, 154, 158, 165, 169, 176, 179, 182, 185, 188,
|
||||
194, 195, 196, 197, 198, 199, 200, 201, 202, 203,
|
||||
204, 205, 206, 207, 208, 209, 210, 211, 212, 213,
|
||||
214, 215, 216, 217
|
||||
0, 63, 63, 65, 69, 70, 74, 75, 84, 85,
|
||||
88, 91, 94, 97, 100, 103, 105, 107, 110, 111,
|
||||
112, 113, 114, 118, 119, 122, 123, 127, 133, 137,
|
||||
144, 148, 155, 157, 159, 163, 166, 169, 172, 178,
|
||||
179, 180, 181, 182, 183, 184, 185, 186, 187, 188,
|
||||
189, 190, 191, 192, 193, 194, 195, 196, 197, 198,
|
||||
199, 200, 201
|
||||
};
|
||||
#endif
|
||||
|
||||
@ -532,16 +519,16 @@ static const yytype_uint8 yyrline[] =
|
||||
First, the terminals, then, starting at YYNTOKENS, nonterminals. */
|
||||
static const char *const yytname[] =
|
||||
{
|
||||
"$end", "error", "$undefined", "HASH", "HASH_DEFINE_OBJ",
|
||||
"HASH_DEFINE_FUNC", "HASH_UNDEF", "HASH_IF", "HASH_IFDEF", "HASH_IFNDEF",
|
||||
"HASH_ELSE", "HASH_ELIF", "HASH_ENDIF", "DEFINED", "HASH_ERROR",
|
||||
"HASH_PRAGMA", "HASH_EXTENSION", "HASH_VERSION", "HASH_LINE", "SPACE",
|
||||
"INT_CONSTANT", "FLOAT_CONSTANT", "IDENTIFIER", "'\\n'", "'('", "')'",
|
||||
"','", "'['", "']'", "'<'", "'>'", "'{'", "'}'", "'.'", "'+'", "'-'",
|
||||
"'/'", "'*'", "'%'", "'^'", "'|'", "'&'", "'~'", "'='", "'!'", "':'",
|
||||
"';'", "'?'", "$accept", "input", "line", "text_line", "control_line",
|
||||
"replacement_token_list", "conditional_token_list", "conditional_token",
|
||||
"parameter_list", "token_list", "token", "operator", 0
|
||||
"$end", "error", "$undefined", "HASH", "HASH_UNDEF", "HASH_IF",
|
||||
"HASH_IFDEF", "HASH_IFNDEF", "HASH_ELSE", "HASH_ELIF", "HASH_ENDIF",
|
||||
"DEFINED", "HASH_ERROR", "HASH_PRAGMA", "HASH_EXTENSION", "HASH_VERSION",
|
||||
"HASH_LINE", "HASH_DEFINE_OBJ", "HASH_DEFINE_FUNC", "INT_CONSTANT",
|
||||
"FLOAT_CONSTANT", "IDENTIFIER", "'\\n'", "'('", "')'", "','", "'['",
|
||||
"']'", "'<'", "'>'", "'{'", "'}'", "'.'", "'+'", "'-'", "'/'", "'*'",
|
||||
"'%'", "'^'", "'|'", "'&'", "'~'", "'='", "'!'", "':'", "';'", "'?'",
|
||||
"$accept", "input", "line", "text_line", "control_line",
|
||||
"replacement_list", "parameter_list", "conditional_list", "token_list",
|
||||
"conditional_token", "token", "operator", 0
|
||||
};
|
||||
#endif
|
||||
|
||||
@ -552,34 +539,34 @@ static const yytype_uint16 yytoknum[] =
|
||||
{
|
||||
0, 256, 257, 258, 259, 260, 261, 262, 263, 264,
|
||||
265, 266, 267, 268, 269, 270, 271, 272, 273, 274,
|
||||
275, 276, 277, 10, 40, 41, 44, 91, 93, 60,
|
||||
62, 123, 125, 46, 43, 45, 47, 42, 37, 94,
|
||||
124, 38, 126, 61, 33, 58, 59, 63
|
||||
275, 276, 10, 40, 41, 44, 91, 93, 60, 62,
|
||||
123, 125, 46, 43, 45, 47, 42, 37, 94, 124,
|
||||
38, 126, 61, 33, 58, 59, 63
|
||||
};
|
||||
# endif
|
||||
|
||||
/* YYR1[YYN] -- Symbol number of symbol that rule YYN derives. */
|
||||
static const yytype_uint8 yyr1[] =
|
||||
{
|
||||
0, 48, 49, 49, 50, 50, 51, 51, 52, 52,
|
||||
52, 52, 52, 52, 52, 52, 52, 52, 52, 52,
|
||||
52, 52, 52, 53, 53, 54, 54, 55, 55, 55,
|
||||
56, 56, 56, 57, 57, 58, 58, 58, 58, 58,
|
||||
59, 59, 59, 59, 59, 59, 59, 59, 59, 59,
|
||||
59, 59, 59, 59, 59, 59, 59, 59, 59, 59,
|
||||
59, 59, 59, 59
|
||||
0, 47, 48, 48, 49, 49, 50, 50, 51, 51,
|
||||
51, 51, 51, 51, 51, 51, 51, 51, 51, 51,
|
||||
51, 51, 51, 52, 52, 53, 53, 53, 54, 54,
|
||||
55, 55, 56, 56, 56, 57, 57, 57, 57, 58,
|
||||
58, 58, 58, 58, 58, 58, 58, 58, 58, 58,
|
||||
58, 58, 58, 58, 58, 58, 58, 58, 58, 58,
|
||||
58, 58, 58
|
||||
};
|
||||
|
||||
/* YYR2[YYN] -- Number of symbols composing right hand side of rule YYN. */
|
||||
static const yytype_uint8 yyr2[] =
|
||||
{
|
||||
0, 2, 0, 2, 1, 1, 1, 2, 2, 4,
|
||||
7, 3, 3, 3, 3, 3, 2, 2, 2, 2,
|
||||
2, 2, 2, 0, 1, 1, 2, 2, 4, 1,
|
||||
0, 1, 3, 1, 2, 1, 1, 1, 1, 1,
|
||||
0, 2, 0, 2, 1, 1, 1, 2, 2, 3,
|
||||
6, 3, 3, 3, 3, 3, 2, 2, 2, 2,
|
||||
2, 2, 2, 0, 1, 0, 1, 3, 1, 2,
|
||||
1, 2, 2, 4, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1
|
||||
1, 1, 1
|
||||
};
|
||||
|
||||
/* YYDEFACT[STATE-NAME] -- Default rule to reduce with in state
|
||||
@ -588,46 +575,46 @@ static const yytype_uint8 yyr2[] =
|
||||
static const yytype_uint8 yydefact[] =
|
||||
{
|
||||
2, 0, 1, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 36, 37,
|
||||
38, 39, 6, 44, 45, 62, 40, 41, 42, 43,
|
||||
0, 0, 0, 0, 0, 0, 23, 0, 36, 37,
|
||||
38, 6, 43, 44, 61, 39, 40, 41, 42, 45,
|
||||
46, 47, 48, 49, 50, 51, 52, 53, 54, 55,
|
||||
56, 57, 58, 59, 60, 61, 63, 3, 4, 5,
|
||||
0, 33, 35, 8, 23, 0, 0, 0, 0, 25,
|
||||
29, 0, 0, 16, 0, 17, 18, 19, 20, 21,
|
||||
22, 7, 34, 0, 24, 30, 11, 27, 0, 12,
|
||||
26, 13, 14, 15, 9, 31, 0, 0, 23, 0,
|
||||
28, 0, 32, 10
|
||||
56, 57, 58, 59, 60, 62, 3, 4, 5, 0,
|
||||
30, 35, 8, 0, 0, 0, 28, 34, 0, 0,
|
||||
16, 0, 17, 18, 19, 20, 21, 22, 0, 24,
|
||||
25, 7, 31, 11, 32, 0, 12, 29, 13, 14,
|
||||
15, 9, 26, 0, 0, 23, 0, 33, 0, 27,
|
||||
10
|
||||
};
|
||||
|
||||
/* YYDEFGOTO[NTERM-NUM]. */
|
||||
static const yytype_int8 yydefgoto[] =
|
||||
{
|
||||
-1, 1, 47, 48, 49, 73, 58, 59, 86, 74,
|
||||
60, 52
|
||||
-1, 1, 46, 47, 48, 68, 83, 55, 69, 56,
|
||||
57, 51
|
||||
};
|
||||
|
||||
/* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing
|
||||
STATE-NUM. */
|
||||
#define YYPACT_NINF -29
|
||||
#define YYPACT_NINF -55
|
||||
static const yytype_int16 yypact[] =
|
||||
{
|
||||
-29, 1, -29, -9, 29, 33, 35, 139, 36, 37,
|
||||
38, 139, 39, 40, 41, 42, 43, 44, -29, -29,
|
||||
-29, -29, -29, -29, -29, -29, -29, -29, -29, -29,
|
||||
-29, -29, -29, -29, -29, -29, -29, -29, -29, -29,
|
||||
-29, -29, -29, -29, -29, -29, -29, -29, -29, -29,
|
||||
168, -29, -29, -29, 197, 45, 47, 30, 69, -29,
|
||||
-29, 48, 49, -29, 104, -29, -29, -29, -29, -29,
|
||||
-29, -29, -29, 51, 197, 46, -29, -29, 53, -29,
|
||||
-29, -29, -29, -29, -29, -29, -23, 52, 197, 54,
|
||||
-29, 55, -29, -29
|
||||
-55, 73, -55, -17, -18, 145, -10, -9, -16, 145,
|
||||
-8, 22, 23, 24, 25, 27, 201, 28, -55, -55,
|
||||
-55, -55, -55, -55, -55, -55, -55, -55, -55, -55,
|
||||
-55, -55, -55, -55, -55, -55, -55, -55, -55, -55,
|
||||
-55, -55, -55, -55, -55, -55, -55, -55, -55, 173,
|
||||
-55, -55, -55, 30, -19, -3, -55, -55, 31, 32,
|
||||
-55, 109, -55, -55, -55, -55, -55, -55, 33, 201,
|
||||
29, -55, -55, -55, -55, 35, -55, -55, -55, -55,
|
||||
-55, -55, -55, -15, -11, 201, 36, -55, 37, -55,
|
||||
-55
|
||||
};
|
||||
|
||||
/* YYPGOTO[NTERM-NUM]. */
|
||||
static const yytype_int8 yypgoto[] =
|
||||
{
|
||||
-29, -29, -29, -29, -29, -28, 68, -8, -29, 79,
|
||||
-1, -29
|
||||
-55, -55, -55, -55, -55, -27, -55, 51, 60, -54,
|
||||
-1, -55
|
||||
};
|
||||
|
||||
/* YYTABLE[YYPACT[STATE-NUM]]. What to do in state STATE-NUM. If
|
||||
@ -637,76 +624,76 @@ static const yytype_int8 yypgoto[] =
|
||||
#define YYTABLE_NINF -1
|
||||
static const yytype_uint8 yytable[] =
|
||||
{
|
||||
51, 2, 88, 89, 3, 4, 5, 6, 7, 8,
|
||||
9, 10, 11, 12, 53, 13, 14, 15, 16, 17,
|
||||
18, 19, 20, 21, 22, 23, 24, 25, 26, 27,
|
||||
28, 29, 30, 31, 32, 33, 34, 35, 36, 37,
|
||||
38, 39, 40, 41, 42, 43, 44, 45, 46, 72,
|
||||
80, 54, 77, 51, 78, 55, 80, 56, 61, 62,
|
||||
91, 63, 65, 66, 67, 68, 69, 70, 85, 75,
|
||||
76, 81, 82, 72, 84, 87, 92, 90, 93, 64,
|
||||
50, 0, 57, 0, 0, 0, 0, 51, 18, 19,
|
||||
20, 21, 79, 23, 24, 25, 26, 27, 28, 29,
|
||||
30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
|
||||
40, 41, 42, 43, 44, 45, 46, 57, 0, 0,
|
||||
0, 0, 0, 18, 19, 20, 21, 83, 23, 24,
|
||||
25, 26, 27, 28, 29, 30, 31, 32, 33, 34,
|
||||
35, 36, 37, 38, 39, 40, 41, 42, 43, 44,
|
||||
45, 46, 57, 0, 0, 0, 0, 0, 18, 19,
|
||||
20, 21, 0, 23, 24, 25, 26, 27, 28, 29,
|
||||
30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
|
||||
40, 41, 42, 43, 44, 45, 46, 18, 19, 20,
|
||||
21, 71, 23, 24, 25, 26, 27, 28, 29, 30,
|
||||
31, 32, 33, 34, 35, 36, 37, 38, 39, 40,
|
||||
41, 42, 43, 44, 45, 46, 18, 19, 20, 21,
|
||||
0, 23, 24, 25, 26, 27, 28, 29, 30, 31,
|
||||
50, 77, 74, 53, 75, 52, 60, 77, 54, 85,
|
||||
86, 58, 59, 87, 62, 50, 18, 19, 20, 76,
|
||||
22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
|
||||
32, 33, 34, 35, 36, 37, 38, 39, 40, 41,
|
||||
42, 43, 44, 45, 46
|
||||
42, 43, 44, 45, 63, 64, 65, 66, 72, 67,
|
||||
82, 70, 73, 78, 79, 81, 84, 89, 88, 90,
|
||||
61, 49, 0, 0, 0, 0, 0, 0, 72, 0,
|
||||
0, 0, 0, 2, 0, 0, 3, 4, 5, 6,
|
||||
7, 8, 9, 10, 50, 11, 12, 13, 14, 15,
|
||||
16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
|
||||
26, 27, 28, 29, 30, 31, 32, 33, 34, 35,
|
||||
36, 37, 38, 39, 40, 41, 42, 43, 44, 45,
|
||||
54, 0, 0, 0, 0, 0, 0, 0, 18, 19,
|
||||
20, 80, 22, 23, 24, 25, 26, 27, 28, 29,
|
||||
30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
|
||||
40, 41, 42, 43, 44, 45, 54, 0, 0, 0,
|
||||
0, 0, 0, 0, 18, 19, 20, 0, 22, 23,
|
||||
24, 25, 26, 27, 28, 29, 30, 31, 32, 33,
|
||||
34, 35, 36, 37, 38, 39, 40, 41, 42, 43,
|
||||
44, 45, 18, 19, 20, 71, 22, 23, 24, 25,
|
||||
26, 27, 28, 29, 30, 31, 32, 33, 34, 35,
|
||||
36, 37, 38, 39, 40, 41, 42, 43, 44, 45,
|
||||
18, 19, 20, 0, 22, 23, 24, 25, 26, 27,
|
||||
28, 29, 30, 31, 32, 33, 34, 35, 36, 37,
|
||||
38, 39, 40, 41, 42, 43, 44, 45
|
||||
};
|
||||
|
||||
static const yytype_int8 yycheck[] =
|
||||
{
|
||||
1, 0, 25, 26, 3, 4, 5, 6, 7, 8,
|
||||
9, 10, 11, 12, 23, 14, 15, 16, 17, 18,
|
||||
19, 20, 21, 22, 23, 24, 25, 26, 27, 28,
|
||||
29, 30, 31, 32, 33, 34, 35, 36, 37, 38,
|
||||
39, 40, 41, 42, 43, 44, 45, 46, 47, 50,
|
||||
58, 22, 22, 54, 24, 22, 64, 22, 22, 22,
|
||||
88, 23, 23, 23, 23, 23, 23, 23, 22, 24,
|
||||
23, 23, 23, 74, 23, 22, 22, 25, 23, 11,
|
||||
1, -1, 13, -1, -1, -1, -1, 88, 19, 20,
|
||||
1, 55, 21, 21, 23, 22, 22, 61, 11, 24,
|
||||
25, 21, 21, 24, 22, 16, 19, 20, 21, 22,
|
||||
23, 24, 25, 26, 27, 28, 29, 30, 31, 32,
|
||||
33, 34, 35, 36, 37, 38, 39, 40, 41, 42,
|
||||
43, 44, 45, 46, 22, 22, 22, 22, 49, 22,
|
||||
21, 23, 22, 22, 22, 22, 21, 21, 85, 22,
|
||||
9, 1, -1, -1, -1, -1, -1, -1, 69, -1,
|
||||
-1, -1, -1, 0, -1, -1, 3, 4, 5, 6,
|
||||
7, 8, 9, 10, 85, 12, 13, 14, 15, 16,
|
||||
17, 18, 19, 20, 21, 22, 23, 24, 25, 26,
|
||||
27, 28, 29, 30, 31, 32, 33, 34, 35, 36,
|
||||
37, 38, 39, 40, 41, 42, 43, 44, 45, 46,
|
||||
11, -1, -1, -1, -1, -1, -1, -1, 19, 20,
|
||||
21, 22, 23, 24, 25, 26, 27, 28, 29, 30,
|
||||
31, 32, 33, 34, 35, 36, 37, 38, 39, 40,
|
||||
41, 42, 43, 44, 45, 46, 47, 13, -1, -1,
|
||||
-1, -1, -1, 19, 20, 21, 22, 23, 24, 25,
|
||||
26, 27, 28, 29, 30, 31, 32, 33, 34, 35,
|
||||
36, 37, 38, 39, 40, 41, 42, 43, 44, 45,
|
||||
46, 47, 13, -1, -1, -1, -1, -1, 19, 20,
|
||||
21, 22, -1, 24, 25, 26, 27, 28, 29, 30,
|
||||
31, 32, 33, 34, 35, 36, 37, 38, 39, 40,
|
||||
41, 42, 43, 44, 45, 46, 47, 19, 20, 21,
|
||||
22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
|
||||
32, 33, 34, 35, 36, 37, 38, 39, 40, 41,
|
||||
42, 43, 44, 45, 46, 47, 19, 20, 21, 22,
|
||||
-1, 24, 25, 26, 27, 28, 29, 30, 31, 32,
|
||||
33, 34, 35, 36, 37, 38, 39, 40, 41, 42,
|
||||
43, 44, 45, 46, 47
|
||||
41, 42, 43, 44, 45, 46, 11, -1, -1, -1,
|
||||
-1, -1, -1, -1, 19, 20, 21, -1, 23, 24,
|
||||
25, 26, 27, 28, 29, 30, 31, 32, 33, 34,
|
||||
35, 36, 37, 38, 39, 40, 41, 42, 43, 44,
|
||||
45, 46, 19, 20, 21, 22, 23, 24, 25, 26,
|
||||
27, 28, 29, 30, 31, 32, 33, 34, 35, 36,
|
||||
37, 38, 39, 40, 41, 42, 43, 44, 45, 46,
|
||||
19, 20, 21, -1, 23, 24, 25, 26, 27, 28,
|
||||
29, 30, 31, 32, 33, 34, 35, 36, 37, 38,
|
||||
39, 40, 41, 42, 43, 44, 45, 46
|
||||
};
|
||||
|
||||
/* YYSTOS[STATE-NUM] -- The (internal number of the) accessing
|
||||
symbol of state STATE-NUM. */
|
||||
static const yytype_uint8 yystos[] =
|
||||
{
|
||||
0, 49, 0, 3, 4, 5, 6, 7, 8, 9,
|
||||
10, 11, 12, 14, 15, 16, 17, 18, 19, 20,
|
||||
0, 48, 0, 3, 4, 5, 6, 7, 8, 9,
|
||||
10, 12, 13, 14, 15, 16, 17, 18, 19, 20,
|
||||
21, 22, 23, 24, 25, 26, 27, 28, 29, 30,
|
||||
31, 32, 33, 34, 35, 36, 37, 38, 39, 40,
|
||||
41, 42, 43, 44, 45, 46, 47, 50, 51, 52,
|
||||
57, 58, 59, 23, 22, 22, 22, 13, 54, 55,
|
||||
58, 22, 22, 23, 54, 23, 23, 23, 23, 23,
|
||||
23, 23, 58, 53, 57, 24, 23, 22, 24, 23,
|
||||
55, 23, 23, 23, 23, 22, 56, 22, 25, 26,
|
||||
25, 53, 22, 23
|
||||
41, 42, 43, 44, 45, 46, 49, 50, 51, 55,
|
||||
57, 58, 22, 21, 11, 54, 56, 57, 21, 21,
|
||||
22, 54, 22, 22, 22, 22, 22, 22, 52, 55,
|
||||
23, 22, 57, 22, 21, 23, 22, 56, 22, 22,
|
||||
22, 22, 21, 53, 21, 24, 25, 24, 52, 21,
|
||||
22
|
||||
};
|
||||
|
||||
#define yyerrok (yyerrstatus = 0)
|
||||
@ -1548,44 +1535,34 @@ yyreduce:
|
||||
YY_REDUCE_PRINT (yyn);
|
||||
switch (yyn)
|
||||
{
|
||||
case 4:
|
||||
case 7:
|
||||
|
||||
{
|
||||
// TODO(alokp): Expand macros.
|
||||
pp::TokenVector* out = context->output;
|
||||
out->insert(out->end(), (yyvsp[(1) - (1)].tlist)->begin(), (yyvsp[(1) - (1)].tlist)->end());
|
||||
delete (yyvsp[(1) - (1)].tlist);
|
||||
pp::TokenVector* out = context->output();
|
||||
out->insert(out->end(), (yyvsp[(1) - (2)].tlist)->begin(), (yyvsp[(1) - (2)].tlist)->end());
|
||||
delete (yyvsp[(1) - (2)].tlist);
|
||||
;}
|
||||
break;
|
||||
|
||||
case 6:
|
||||
|
||||
{ (yyval.tlist) = NULL; ;}
|
||||
break;
|
||||
|
||||
case 7:
|
||||
|
||||
{ (yyval.tlist) = (yyvsp[(1) - (2)].tlist); ;}
|
||||
break;
|
||||
|
||||
case 9:
|
||||
|
||||
{
|
||||
defineMacro(context, & (yylsp[(2) - (4)]), pp::Macro::kTypeObj, (yyvsp[(2) - (4)].sval), NULL, (yyvsp[(3) - (4)].tlist));
|
||||
context->defineMacro((yylsp[(1) - (3)]).first_line, pp::Macro::kTypeObj, (yyvsp[(1) - (3)].sval), NULL, (yyvsp[(2) - (3)].tlist));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 10:
|
||||
|
||||
{
|
||||
defineMacro(context, & (yylsp[(2) - (7)]), pp::Macro::kTypeFunc, (yyvsp[(2) - (7)].sval), (yyvsp[(4) - (7)].slist), (yyvsp[(6) - (7)].tlist));
|
||||
context->defineMacro((yylsp[(1) - (6)]).first_line, pp::Macro::kTypeFunc, (yyvsp[(1) - (6)].sval), (yyvsp[(3) - (6)].tlist), (yyvsp[(5) - (6)].tlist));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 11:
|
||||
|
||||
{
|
||||
undefineMacro(context, (yyvsp[(2) - (3)].sval));
|
||||
context->undefineMacro((yyvsp[(2) - (3)].sval));
|
||||
;}
|
||||
break;
|
||||
|
||||
@ -1599,14 +1576,14 @@ yyreduce:
|
||||
case 13:
|
||||
|
||||
{
|
||||
pushConditionalBlock(context, isMacroDefined(context, (yyvsp[(2) - (3)].sval)));
|
||||
pushConditionalBlock(context, context->isMacroDefined((yyvsp[(2) - (3)].sval)));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 14:
|
||||
|
||||
{
|
||||
pushConditionalBlock(context, !isMacroDefined(context, (yyvsp[(2) - (3)].sval)));
|
||||
pushConditionalBlock(context, !context->isMacroDefined((yyvsp[(2) - (3)].sval)));
|
||||
;}
|
||||
break;
|
||||
|
||||
@ -1631,67 +1608,39 @@ yyreduce:
|
||||
|
||||
case 23:
|
||||
|
||||
{ (yyval.tlist) = NULL ;}
|
||||
{ (yyval.tlist) = NULL; ;}
|
||||
break;
|
||||
|
||||
case 25:
|
||||
|
||||
{
|
||||
(yyval.tlist) = new pp::TokenVector;
|
||||
(yyval.tlist)->push_back((yyvsp[(1) - (1)].tval));
|
||||
;}
|
||||
{ (yyval.tlist) = NULL; ;}
|
||||
break;
|
||||
|
||||
case 26:
|
||||
|
||||
{
|
||||
(yyval.tlist) = (yyvsp[(1) - (2)].tlist);
|
||||
(yyval.tlist)->push_back((yyvsp[(2) - (2)].tval));
|
||||
(yyval.tlist) = new pp::TokenVector;
|
||||
(yyval.tlist)->push_back(new pp::Token((yylsp[(1) - (1)]).first_line, IDENTIFIER, (yyvsp[(1) - (1)].sval)));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 27:
|
||||
|
||||
{
|
||||
(yyval.tlist) = (yyvsp[(1) - (3)].tlist);
|
||||
(yyval.tlist)->push_back(new pp::Token((yylsp[(3) - (3)]).first_line, IDENTIFIER, (yyvsp[(3) - (3)].sval)));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 28:
|
||||
|
||||
{
|
||||
;}
|
||||
break;
|
||||
|
||||
case 30:
|
||||
|
||||
{ (yyval.slist) = NULL; ;}
|
||||
break;
|
||||
|
||||
case 31:
|
||||
|
||||
{
|
||||
(yyval.slist) = new std::vector<std::string*>();
|
||||
(yyval.slist)->push_back((yyvsp[(1) - (1)].sval));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 32:
|
||||
|
||||
{
|
||||
(yyval.slist) = (yyvsp[(1) - (3)].slist);
|
||||
(yyval.slist)->push_back((yyvsp[(3) - (3)].sval));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 33:
|
||||
|
||||
{
|
||||
(yyval.tlist) = new pp::TokenVector;
|
||||
(yyval.tlist)->push_back((yyvsp[(1) - (1)].tval));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 34:
|
||||
case 29:
|
||||
|
||||
{
|
||||
(yyval.tlist) = (yyvsp[(1) - (2)].tlist);
|
||||
@ -1699,6 +1648,34 @@ yyreduce:
|
||||
;}
|
||||
break;
|
||||
|
||||
case 30:
|
||||
|
||||
{
|
||||
(yyval.tlist) = new pp::TokenVector;
|
||||
(yyval.tlist)->push_back((yyvsp[(1) - (1)].tval));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 31:
|
||||
|
||||
{
|
||||
(yyval.tlist) = (yyvsp[(1) - (2)].tlist);
|
||||
(yyval.tlist)->push_back((yyvsp[(2) - (2)].tval));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 32:
|
||||
|
||||
{
|
||||
;}
|
||||
break;
|
||||
|
||||
case 33:
|
||||
|
||||
{
|
||||
;}
|
||||
break;
|
||||
|
||||
case 35:
|
||||
|
||||
{
|
||||
@ -1709,147 +1686,140 @@ yyreduce:
|
||||
case 36:
|
||||
|
||||
{
|
||||
(yyval.tval) = new pp::Token((yylsp[(1) - (1)]).first_line, SPACE, NULL);
|
||||
(yyval.tval) = new pp::Token((yylsp[(1) - (1)]).first_line, INT_CONSTANT, (yyvsp[(1) - (1)].sval));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 37:
|
||||
|
||||
{
|
||||
(yyval.tval) = new pp::Token((yylsp[(1) - (1)]).first_line, INT_CONSTANT, (yyvsp[(1) - (1)].sval));
|
||||
(yyval.tval) = new pp::Token((yylsp[(1) - (1)]).first_line, FLOAT_CONSTANT, (yyvsp[(1) - (1)].sval));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 38:
|
||||
|
||||
{
|
||||
(yyval.tval) = new pp::Token((yylsp[(1) - (1)]).first_line, FLOAT_CONSTANT, (yyvsp[(1) - (1)].sval));
|
||||
(yyval.tval) = new pp::Token((yylsp[(1) - (1)]).first_line, IDENTIFIER, (yyvsp[(1) - (1)].sval));
|
||||
;}
|
||||
break;
|
||||
|
||||
case 39:
|
||||
|
||||
{
|
||||
(yyval.tval) = new pp::Token((yylsp[(1) - (1)]).first_line, IDENTIFIER, (yyvsp[(1) - (1)].sval));
|
||||
;}
|
||||
{ (yyval.ival) = '['; ;}
|
||||
break;
|
||||
|
||||
case 40:
|
||||
|
||||
{ (yyval.ival) = '['; ;}
|
||||
{ (yyval.ival) = ']'; ;}
|
||||
break;
|
||||
|
||||
case 41:
|
||||
|
||||
{ (yyval.ival) = ']'; ;}
|
||||
{ (yyval.ival) = '<'; ;}
|
||||
break;
|
||||
|
||||
case 42:
|
||||
|
||||
{ (yyval.ival) = '<'; ;}
|
||||
{ (yyval.ival) = '>'; ;}
|
||||
break;
|
||||
|
||||
case 43:
|
||||
|
||||
{ (yyval.ival) = '>'; ;}
|
||||
{ (yyval.ival) = '('; ;}
|
||||
break;
|
||||
|
||||
case 44:
|
||||
|
||||
{ (yyval.ival) = '('; ;}
|
||||
{ (yyval.ival) = ')'; ;}
|
||||
break;
|
||||
|
||||
case 45:
|
||||
|
||||
{ (yyval.ival) = ')'; ;}
|
||||
{ (yyval.ival) = '{'; ;}
|
||||
break;
|
||||
|
||||
case 46:
|
||||
|
||||
{ (yyval.ival) = '{'; ;}
|
||||
{ (yyval.ival) = '}'; ;}
|
||||
break;
|
||||
|
||||
case 47:
|
||||
|
||||
{ (yyval.ival) = '}'; ;}
|
||||
{ (yyval.ival) = '.'; ;}
|
||||
break;
|
||||
|
||||
case 48:
|
||||
|
||||
{ (yyval.ival) = '.'; ;}
|
||||
{ (yyval.ival) = '+'; ;}
|
||||
break;
|
||||
|
||||
case 49:
|
||||
|
||||
{ (yyval.ival) = '+'; ;}
|
||||
{ (yyval.ival) = '-'; ;}
|
||||
break;
|
||||
|
||||
case 50:
|
||||
|
||||
{ (yyval.ival) = '-'; ;}
|
||||
{ (yyval.ival) = '/'; ;}
|
||||
break;
|
||||
|
||||
case 51:
|
||||
|
||||
{ (yyval.ival) = '/'; ;}
|
||||
{ (yyval.ival) = '*'; ;}
|
||||
break;
|
||||
|
||||
case 52:
|
||||
|
||||
{ (yyval.ival) = '*'; ;}
|
||||
{ (yyval.ival) = '%'; ;}
|
||||
break;
|
||||
|
||||
case 53:
|
||||
|
||||
{ (yyval.ival) = '%'; ;}
|
||||
{ (yyval.ival) = '^'; ;}
|
||||
break;
|
||||
|
||||
case 54:
|
||||
|
||||
{ (yyval.ival) = '^'; ;}
|
||||
{ (yyval.ival) = '|'; ;}
|
||||
break;
|
||||
|
||||
case 55:
|
||||
|
||||
{ (yyval.ival) = '|'; ;}
|
||||
{ (yyval.ival) = '&'; ;}
|
||||
break;
|
||||
|
||||
case 56:
|
||||
|
||||
{ (yyval.ival) = '&'; ;}
|
||||
{ (yyval.ival) = '~'; ;}
|
||||
break;
|
||||
|
||||
case 57:
|
||||
|
||||
{ (yyval.ival) = '~'; ;}
|
||||
{ (yyval.ival) = '='; ;}
|
||||
break;
|
||||
|
||||
case 58:
|
||||
|
||||
{ (yyval.ival) = '='; ;}
|
||||
{ (yyval.ival) = '!'; ;}
|
||||
break;
|
||||
|
||||
case 59:
|
||||
|
||||
{ (yyval.ival) = '!'; ;}
|
||||
{ (yyval.ival) = ':'; ;}
|
||||
break;
|
||||
|
||||
case 60:
|
||||
|
||||
{ (yyval.ival) = ':'; ;}
|
||||
{ (yyval.ival) = ';'; ;}
|
||||
break;
|
||||
|
||||
case 61:
|
||||
|
||||
{ (yyval.ival) = ';'; ;}
|
||||
break;
|
||||
|
||||
case 62:
|
||||
|
||||
{ (yyval.ival) = ','; ;}
|
||||
break;
|
||||
|
||||
case 63:
|
||||
case 62:
|
||||
|
||||
{ (yyval.ival) = '?'; ;}
|
||||
break;
|
||||
@ -2083,24 +2053,6 @@ void yyerror(YYLTYPE* llocp, pp::Context* context, const char* reason)
|
||||
{
|
||||
}
|
||||
|
||||
void defineMacro(pp::Context* context,
|
||||
YYLTYPE* llocp,
|
||||
pp::Macro::Type type,
|
||||
const std::string* identifier,
|
||||
std::vector<std::string*>* parameters,
|
||||
pp::TokenVector* replacements)
|
||||
{
|
||||
}
|
||||
|
||||
void undefineMacro(pp::Context* context, const std::string* identifier)
|
||||
{
|
||||
}
|
||||
|
||||
bool isMacroDefined(pp::Context* context, const std::string* identifier)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
void pushConditionalBlock(pp::Context* context, bool condition)
|
||||
{
|
||||
}
|
||||
@ -2110,10 +2062,10 @@ void popConditionalBlock(pp::Context* context)
|
||||
}
|
||||
|
||||
namespace pp {
|
||||
bool Preprocessor::parse(Context* context)
|
||||
bool Context::parse()
|
||||
{
|
||||
yydebug = 1;
|
||||
return yyparse(context) == 0 ? true : false;
|
||||
return yyparse(this) == 0 ? true : false;
|
||||
}
|
||||
} // namespace pp
|
||||
|
||||
|
@ -40,48 +40,46 @@
|
||||
know about them. */
|
||||
enum yytokentype {
|
||||
HASH = 258,
|
||||
HASH_DEFINE_OBJ = 259,
|
||||
HASH_DEFINE_FUNC = 260,
|
||||
HASH_UNDEF = 261,
|
||||
HASH_IF = 262,
|
||||
HASH_IFDEF = 263,
|
||||
HASH_IFNDEF = 264,
|
||||
HASH_ELSE = 265,
|
||||
HASH_ELIF = 266,
|
||||
HASH_ENDIF = 267,
|
||||
DEFINED = 268,
|
||||
HASH_ERROR = 269,
|
||||
HASH_PRAGMA = 270,
|
||||
HASH_EXTENSION = 271,
|
||||
HASH_VERSION = 272,
|
||||
HASH_LINE = 273,
|
||||
SPACE = 274,
|
||||
INT_CONSTANT = 275,
|
||||
FLOAT_CONSTANT = 276,
|
||||
IDENTIFIER = 277
|
||||
HASH_UNDEF = 259,
|
||||
HASH_IF = 260,
|
||||
HASH_IFDEF = 261,
|
||||
HASH_IFNDEF = 262,
|
||||
HASH_ELSE = 263,
|
||||
HASH_ELIF = 264,
|
||||
HASH_ENDIF = 265,
|
||||
DEFINED = 266,
|
||||
HASH_ERROR = 267,
|
||||
HASH_PRAGMA = 268,
|
||||
HASH_EXTENSION = 269,
|
||||
HASH_VERSION = 270,
|
||||
HASH_LINE = 271,
|
||||
HASH_DEFINE_OBJ = 272,
|
||||
HASH_DEFINE_FUNC = 273,
|
||||
INT_CONSTANT = 274,
|
||||
FLOAT_CONSTANT = 275,
|
||||
IDENTIFIER = 276
|
||||
};
|
||||
#endif
|
||||
/* Tokens. */
|
||||
#define HASH 258
|
||||
#define HASH_DEFINE_OBJ 259
|
||||
#define HASH_DEFINE_FUNC 260
|
||||
#define HASH_UNDEF 261
|
||||
#define HASH_IF 262
|
||||
#define HASH_IFDEF 263
|
||||
#define HASH_IFNDEF 264
|
||||
#define HASH_ELSE 265
|
||||
#define HASH_ELIF 266
|
||||
#define HASH_ENDIF 267
|
||||
#define DEFINED 268
|
||||
#define HASH_ERROR 269
|
||||
#define HASH_PRAGMA 270
|
||||
#define HASH_EXTENSION 271
|
||||
#define HASH_VERSION 272
|
||||
#define HASH_LINE 273
|
||||
#define SPACE 274
|
||||
#define INT_CONSTANT 275
|
||||
#define FLOAT_CONSTANT 276
|
||||
#define IDENTIFIER 277
|
||||
#define HASH_UNDEF 259
|
||||
#define HASH_IF 260
|
||||
#define HASH_IFDEF 261
|
||||
#define HASH_IFNDEF 262
|
||||
#define HASH_ELSE 263
|
||||
#define HASH_ELIF 264
|
||||
#define HASH_ENDIF 265
|
||||
#define DEFINED 266
|
||||
#define HASH_ERROR 267
|
||||
#define HASH_PRAGMA 268
|
||||
#define HASH_EXTENSION 269
|
||||
#define HASH_VERSION 270
|
||||
#define HASH_LINE 271
|
||||
#define HASH_DEFINE_OBJ 272
|
||||
#define HASH_DEFINE_FUNC 273
|
||||
#define INT_CONSTANT 274
|
||||
#define FLOAT_CONSTANT 275
|
||||
#define IDENTIFIER 276
|
||||
|
||||
|
||||
|
||||
@ -92,7 +90,6 @@ typedef union YYSTYPE
|
||||
{
|
||||
int ival;
|
||||
std::string* sval;
|
||||
std::vector<std::string*>* slist;
|
||||
pp::Token* tval;
|
||||
pp::TokenVector* tlist;
|
||||
}
|
||||
|
@ -515,6 +515,11 @@ EGLSurface Display::createWindowSurface(HWND window, EGLConfig config, const EGL
|
||||
return error(EGL_BAD_ALLOC, EGL_NO_SURFACE);
|
||||
}
|
||||
|
||||
if (isDeviceLost()) {
|
||||
if (!restoreLostDevice())
|
||||
return EGL_NO_SURFACE;
|
||||
}
|
||||
|
||||
Surface *surface = new Surface(this, configuration, window);
|
||||
|
||||
if (!surface->initialize())
|
||||
@ -622,6 +627,11 @@ EGLSurface Display::createOffscreenSurface(EGLConfig config, HANDLE shareHandle,
|
||||
return error(EGL_BAD_ATTRIBUTE, EGL_NO_SURFACE);
|
||||
}
|
||||
|
||||
if (isDeviceLost()) {
|
||||
if (!restoreLostDevice())
|
||||
return EGL_NO_SURFACE;
|
||||
}
|
||||
|
||||
Surface *surface = new Surface(this, configuration, shareHandle, width, height, textureFormat, textureTarget);
|
||||
|
||||
if (!surface->initialize())
|
||||
@ -646,24 +656,10 @@ EGLContext Display::createContext(EGLConfig configHandle, const gl::Context *sha
|
||||
}
|
||||
else if (isDeviceLost()) // Lost device
|
||||
{
|
||||
// Release surface resources to make the Reset() succeed
|
||||
for (SurfaceSet::iterator surface = mSurfaceSet.begin(); surface != mSurfaceSet.end(); surface++)
|
||||
{
|
||||
(*surface)->release();
|
||||
}
|
||||
|
||||
if (!resetDevice())
|
||||
{
|
||||
if (!restoreLostDevice())
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Restore any surfaces that may have been lost
|
||||
for (SurfaceSet::iterator surface = mSurfaceSet.begin(); surface != mSurfaceSet.end(); surface++)
|
||||
{
|
||||
(*surface)->resetSwapChain();
|
||||
}
|
||||
}
|
||||
|
||||
const egl::Config *config = mConfigSet.get(configHandle);
|
||||
|
||||
gl::Context *context = glCreateContext(config, shareContext);
|
||||
@ -672,6 +668,29 @@ EGLContext Display::createContext(EGLConfig configHandle, const gl::Context *sha
|
||||
return context;
|
||||
}
|
||||
|
||||
bool Display::restoreLostDevice()
|
||||
{
|
||||
// Release surface resources to make the Reset() succeed
|
||||
for (SurfaceSet::iterator surface = mSurfaceSet.begin(); surface != mSurfaceSet.end(); surface++)
|
||||
{
|
||||
(*surface)->release();
|
||||
}
|
||||
|
||||
if (!resetDevice())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// Restore any surfaces that may have been lost
|
||||
for (SurfaceSet::iterator surface = mSurfaceSet.begin(); surface != mSurfaceSet.end(); surface++)
|
||||
{
|
||||
(*surface)->resetSwapChain();
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
void Display::destroySurface(egl::Surface *surface)
|
||||
{
|
||||
delete surface;
|
||||
@ -756,10 +775,12 @@ bool Display::isDeviceLost()
|
||||
{
|
||||
return FAILED(mDeviceEx->CheckDeviceState(NULL));
|
||||
}
|
||||
else
|
||||
else if(mDevice)
|
||||
{
|
||||
return FAILED(mDevice->TestCooperativeLevel());
|
||||
}
|
||||
|
||||
return false; // No device yet, so no reset required
|
||||
}
|
||||
|
||||
void Display::getMultiSampleSupport(D3DFORMAT format, bool *multiSampleArray)
|
||||
@ -922,17 +943,24 @@ D3DPRESENT_PARAMETERS Display::getDefaultPresentParameters()
|
||||
|
||||
void Display::initExtensionString()
|
||||
{
|
||||
mExtensionString += "EGL_ANGLE_query_surface_pointer ";
|
||||
HMODULE swiftShader = GetModuleHandle(TEXT("swiftshader_d3d9.dll"));
|
||||
bool isd3d9ex = isD3d9ExDevice();
|
||||
|
||||
mExtensionString = "";
|
||||
|
||||
if (isd3d9ex) {
|
||||
mExtensionString += "EGL_ANGLE_d3d_share_handle_client_buffer ";
|
||||
}
|
||||
|
||||
mExtensionString += "EGL_ANGLE_query_surface_pointer ";
|
||||
|
||||
if (swiftShader)
|
||||
{
|
||||
mExtensionString += "EGL_ANGLE_software_display ";
|
||||
}
|
||||
|
||||
if (isD3d9ExDevice()) {
|
||||
if (isd3d9ex) {
|
||||
mExtensionString += "EGL_ANGLE_surface_d3d_texture_2d_share_handle ";
|
||||
mExtensionString += "EGL_ANGLE_d3d_share_handle_client_buffer ";
|
||||
}
|
||||
|
||||
std::string::size_type end = mExtensionString.find_last_not_of(' ');
|
||||
|
@ -85,6 +85,8 @@ class Display
|
||||
|
||||
D3DPRESENT_PARAMETERS getDefaultPresentParameters();
|
||||
|
||||
bool restoreLostDevice();
|
||||
|
||||
EGLNativeDisplayType mDisplayId;
|
||||
const HDC mDc;
|
||||
|
||||
|
@ -191,8 +191,26 @@ bool Surface::resetSwapChain(int backbufferWidth, int backbufferHeight)
|
||||
// the current process, disable use of FlipEx.
|
||||
DWORD windowPID;
|
||||
GetWindowThreadProcessId(mWindow, &windowPID);
|
||||
if(windowPID != GetCurrentProcessId())
|
||||
if (windowPID != GetCurrentProcessId())
|
||||
{
|
||||
useFlipEx = false;
|
||||
}
|
||||
|
||||
// Various hardware does not support D3DSWAPEFFECT_FLIPEX when either the
|
||||
// device format or back buffer format is not 32-bit.
|
||||
HDC deviceContext = GetDC(0);
|
||||
int deviceFormatBits = GetDeviceCaps(deviceContext, BITSPIXEL);
|
||||
ReleaseDC(0, deviceContext);
|
||||
if (mConfig->mBufferSize != 32 || deviceFormatBits != 32)
|
||||
{
|
||||
useFlipEx = false;
|
||||
}
|
||||
|
||||
// D3DSWAPEFFECT_FLIPEX is always VSYNCed
|
||||
if (mSwapInterval == 0)
|
||||
{
|
||||
useFlipEx = false;
|
||||
}
|
||||
|
||||
presentParameters.AutoDepthStencilFormat = mConfig->mDepthStencilFormat;
|
||||
// We set BackBufferCount = 1 even when we use D3DSWAPEFFECT_FLIPEX.
|
||||
|
@ -7,7 +7,7 @@
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#include "afxres.h"
|
||||
#include <windows.h>
|
||||
#include "../common/version.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -74,6 +74,8 @@ void Buffer::bufferSubData(const void *data, GLsizeiptr size, GLintptr offset)
|
||||
{
|
||||
invalidateStaticData();
|
||||
}
|
||||
|
||||
mUnmodifiedDataUse = 0;
|
||||
}
|
||||
|
||||
StaticVertexBuffer *Buffer::getStaticVertexBuffer()
|
||||
|
@ -363,7 +363,12 @@ void Context::markAllStateDirty()
|
||||
mAppliedRenderTargetSerial = 0;
|
||||
mAppliedDepthbufferSerial = 0;
|
||||
mAppliedStencilbufferSerial = 0;
|
||||
mAppliedIBSerial = 0;
|
||||
mDepthStencilInitialized = false;
|
||||
mViewportInitialized = false;
|
||||
mRenderTargetDescInitialized = false;
|
||||
|
||||
mVertexDeclarationCache.markStateDirty();
|
||||
|
||||
mClearStateDirty = true;
|
||||
mCullStateDirty = true;
|
||||
@ -1618,12 +1623,14 @@ bool Context::applyRenderTarget(bool ignoreViewport)
|
||||
|
||||
IDirect3DSurface9 *depthStencil = NULL;
|
||||
|
||||
bool renderTargetChanged = false;
|
||||
unsigned int renderTargetSerial = framebufferObject->getRenderTargetSerial();
|
||||
if (renderTargetSerial != mAppliedRenderTargetSerial)
|
||||
{
|
||||
device->SetRenderTarget(0, renderTarget);
|
||||
mAppliedRenderTargetSerial = renderTargetSerial;
|
||||
mScissorStateDirty = true; // Scissor area must be clamped to render target's size-- this is different for different render targets.
|
||||
renderTargetChanged = true;
|
||||
}
|
||||
|
||||
unsigned int depthbufferSerial = 0;
|
||||
@ -1661,9 +1668,13 @@ bool Context::applyRenderTarget(bool ignoreViewport)
|
||||
mDepthStencilInitialized = true;
|
||||
}
|
||||
|
||||
if (!mRenderTargetDescInitialized || renderTargetChanged)
|
||||
{
|
||||
renderTarget->GetDesc(&mRenderTargetDesc);
|
||||
mRenderTargetDescInitialized = true;
|
||||
}
|
||||
|
||||
D3DVIEWPORT9 viewport;
|
||||
D3DSURFACE_DESC desc;
|
||||
renderTarget->GetDesc(&desc);
|
||||
|
||||
float zNear = clamp01(mState.zNear);
|
||||
float zFar = clamp01(mState.zFar);
|
||||
@ -1672,18 +1683,18 @@ bool Context::applyRenderTarget(bool ignoreViewport)
|
||||
{
|
||||
viewport.X = 0;
|
||||
viewport.Y = 0;
|
||||
viewport.Width = desc.Width;
|
||||
viewport.Height = desc.Height;
|
||||
viewport.Width = mRenderTargetDesc.Width;
|
||||
viewport.Height = mRenderTargetDesc.Height;
|
||||
viewport.MinZ = 0.0f;
|
||||
viewport.MaxZ = 1.0f;
|
||||
}
|
||||
else
|
||||
{
|
||||
RECT rect = transformPixelRect(mState.viewportX, mState.viewportY, mState.viewportWidth, mState.viewportHeight, desc.Height);
|
||||
viewport.X = clamp(rect.left, 0L, static_cast<LONG>(desc.Width));
|
||||
viewport.Y = clamp(rect.top, 0L, static_cast<LONG>(desc.Height));
|
||||
viewport.Width = clamp(rect.right - rect.left, 0L, static_cast<LONG>(desc.Width) - static_cast<LONG>(viewport.X));
|
||||
viewport.Height = clamp(rect.bottom - rect.top, 0L, static_cast<LONG>(desc.Height) - static_cast<LONG>(viewport.Y));
|
||||
RECT rect = transformPixelRect(mState.viewportX, mState.viewportY, mState.viewportWidth, mState.viewportHeight, mRenderTargetDesc.Height);
|
||||
viewport.X = clamp(rect.left, 0L, static_cast<LONG>(mRenderTargetDesc.Width));
|
||||
viewport.Y = clamp(rect.top, 0L, static_cast<LONG>(mRenderTargetDesc.Height));
|
||||
viewport.Width = clamp(rect.right - rect.left, 0L, static_cast<LONG>(mRenderTargetDesc.Width) - static_cast<LONG>(viewport.X));
|
||||
viewport.Height = clamp(rect.bottom - rect.top, 0L, static_cast<LONG>(mRenderTargetDesc.Height) - static_cast<LONG>(viewport.Y));
|
||||
viewport.MinZ = zNear;
|
||||
viewport.MaxZ = zFar;
|
||||
}
|
||||
@ -1693,17 +1704,22 @@ bool Context::applyRenderTarget(bool ignoreViewport)
|
||||
return false; // Nothing to render
|
||||
}
|
||||
|
||||
if (!mViewportInitialized || memcmp(&viewport, &mSetViewport, sizeof mSetViewport) != 0)
|
||||
{
|
||||
device->SetViewport(&viewport);
|
||||
mSetViewport = viewport;
|
||||
mViewportInitialized = true;
|
||||
}
|
||||
|
||||
if (mScissorStateDirty)
|
||||
{
|
||||
if (mState.scissorTest)
|
||||
{
|
||||
RECT rect = transformPixelRect(mState.scissorX, mState.scissorY, mState.scissorWidth, mState.scissorHeight, desc.Height);
|
||||
rect.left = clamp(rect.left, 0L, static_cast<LONG>(desc.Width));
|
||||
rect.top = clamp(rect.top, 0L, static_cast<LONG>(desc.Height));
|
||||
rect.right = clamp(rect.right, 0L, static_cast<LONG>(desc.Width));
|
||||
rect.bottom = clamp(rect.bottom, 0L, static_cast<LONG>(desc.Height));
|
||||
RECT rect = transformPixelRect(mState.scissorX, mState.scissorY, mState.scissorWidth, mState.scissorHeight, mRenderTargetDesc.Height);
|
||||
rect.left = clamp(rect.left, 0L, static_cast<LONG>(mRenderTargetDesc.Width));
|
||||
rect.top = clamp(rect.top, 0L, static_cast<LONG>(mRenderTargetDesc.Height));
|
||||
rect.right = clamp(rect.right, 0L, static_cast<LONG>(mRenderTargetDesc.Width));
|
||||
rect.bottom = clamp(rect.bottom, 0L, static_cast<LONG>(mRenderTargetDesc.Height));
|
||||
device->SetScissorRect(&rect);
|
||||
device->SetRenderState(D3DRS_SCISSORTESTENABLE, TRUE);
|
||||
}
|
||||
@ -2023,8 +2039,12 @@ GLenum Context::applyIndexBuffer(const void *indices, GLsizei count, GLenum mode
|
||||
GLenum err = mIndexDataManager->prepareIndexData(type, count, mState.elementArrayBuffer.get(), indices, indexInfo);
|
||||
|
||||
if (err == GL_NO_ERROR)
|
||||
{
|
||||
if (indexInfo->serial != mAppliedIBSerial)
|
||||
{
|
||||
device->SetIndices(indexInfo->indexBuffer);
|
||||
mAppliedIBSerial = indexInfo->serial;
|
||||
}
|
||||
}
|
||||
|
||||
return err;
|
||||
@ -2035,14 +2055,13 @@ void Context::applyShaders()
|
||||
{
|
||||
IDirect3DDevice9 *device = getDevice();
|
||||
Program *programObject = getCurrentProgram();
|
||||
if (programObject->getSerial() != mAppliedProgramSerial)
|
||||
{
|
||||
IDirect3DVertexShader9 *vertexShader = programObject->getVertexShader();
|
||||
IDirect3DPixelShader9 *pixelShader = programObject->getPixelShader();
|
||||
|
||||
device->SetVertexShader(vertexShader);
|
||||
device->SetPixelShader(pixelShader);
|
||||
|
||||
if (programObject->getSerial() != mAppliedProgramSerial)
|
||||
{
|
||||
device->SetVertexShader(vertexShader);
|
||||
programObject->dirtyAllUniforms();
|
||||
mAppliedProgramSerial = programObject->getSerial();
|
||||
}
|
||||
@ -2510,6 +2529,7 @@ void Context::clear(GLbitfield mask)
|
||||
device->SetPixelShader(NULL);
|
||||
device->SetVertexShader(NULL);
|
||||
device->SetFVF(D3DFVF_XYZRHW | D3DFVF_DIFFUSE);
|
||||
device->SetStreamSource(0, NULL, 0, 0);
|
||||
device->SetRenderState(D3DRS_SEPARATEALPHABLENDENABLE, TRUE);
|
||||
device->SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
|
||||
device->SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TFACTOR);
|
||||
@ -2907,6 +2927,7 @@ void Context::drawClosingLine(unsigned int first, unsigned int last)
|
||||
if (succeeded)
|
||||
{
|
||||
device->SetIndices(mClosingIB->getBuffer());
|
||||
mAppliedIBSerial = mClosingIB->getSerial();
|
||||
|
||||
device->DrawIndexedPrimitive(D3DPT_LINELIST, 0, 0, last, offset, 1);
|
||||
}
|
||||
@ -3348,68 +3369,76 @@ void Context::setVertexAttrib(GLuint index, const GLfloat *values)
|
||||
mVertexDataManager->dirtyCurrentValue(index);
|
||||
}
|
||||
|
||||
// keep list sorted in following order
|
||||
// OES extensions
|
||||
// EXT extensions
|
||||
// Vendor extensions
|
||||
void Context::initExtensionString()
|
||||
{
|
||||
mExtensionString = "";
|
||||
|
||||
// OES extensions
|
||||
if (supports32bitIndices())
|
||||
{
|
||||
mExtensionString += "GL_OES_element_index_uint ";
|
||||
}
|
||||
|
||||
mExtensionString += "GL_OES_packed_depth_stencil ";
|
||||
mExtensionString += "GL_EXT_texture_format_BGRA8888 ";
|
||||
mExtensionString += "GL_EXT_read_format_bgra ";
|
||||
mExtensionString += "GL_ANGLE_framebuffer_blit ";
|
||||
mExtensionString += "GL_OES_rgb8_rgba8 ";
|
||||
mExtensionString += "GL_OES_standard_derivatives ";
|
||||
|
||||
if (supportsEventQueries())
|
||||
if (supportsHalfFloatTextures())
|
||||
{
|
||||
mExtensionString += "GL_NV_fence ";
|
||||
mExtensionString += "GL_OES_texture_half_float ";
|
||||
}
|
||||
if (supportsHalfFloatLinearFilter())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_half_float_linear ";
|
||||
}
|
||||
if (supportsFloatTextures())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_float ";
|
||||
}
|
||||
if (supportsFloatLinearFilter())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_float_linear ";
|
||||
}
|
||||
|
||||
if (supportsNonPower2Texture())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_npot ";
|
||||
}
|
||||
|
||||
// Multi-vendor (EXT) extensions
|
||||
mExtensionString += "GL_EXT_read_format_bgra ";
|
||||
|
||||
if (supportsDXT1Textures())
|
||||
{
|
||||
mExtensionString += "GL_EXT_texture_compression_dxt1 ";
|
||||
}
|
||||
|
||||
if (supportsDXT3Textures())
|
||||
{
|
||||
mExtensionString += "GL_ANGLE_texture_compression_dxt3 ";
|
||||
}
|
||||
|
||||
if (supportsDXT5Textures())
|
||||
{
|
||||
mExtensionString += "GL_ANGLE_texture_compression_dxt5 ";
|
||||
}
|
||||
|
||||
if (supportsFloatTextures())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_float ";
|
||||
}
|
||||
|
||||
if (supportsHalfFloatTextures())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_half_float ";
|
||||
}
|
||||
|
||||
if (supportsFloatLinearFilter())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_float_linear ";
|
||||
}
|
||||
|
||||
if (supportsHalfFloatLinearFilter())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_half_float_linear ";
|
||||
}
|
||||
mExtensionString += "GL_EXT_texture_format_BGRA8888 ";
|
||||
|
||||
// ANGLE-specific extensions
|
||||
mExtensionString += "GL_ANGLE_framebuffer_blit ";
|
||||
if (getMaxSupportedSamples() != 0)
|
||||
{
|
||||
mExtensionString += "GL_ANGLE_framebuffer_multisample ";
|
||||
}
|
||||
|
||||
if (supports32bitIndices())
|
||||
if (supportsDXT3Textures())
|
||||
{
|
||||
mExtensionString += "GL_OES_element_index_uint ";
|
||||
mExtensionString += "GL_ANGLE_texture_compression_dxt3 ";
|
||||
}
|
||||
if (supportsDXT5Textures())
|
||||
{
|
||||
mExtensionString += "GL_ANGLE_texture_compression_dxt5 ";
|
||||
}
|
||||
|
||||
if (supportsNonPower2Texture())
|
||||
// Other vendor-specific extensions
|
||||
if (supportsEventQueries())
|
||||
{
|
||||
mExtensionString += "GL_OES_texture_npot ";
|
||||
mExtensionString += "GL_NV_fence ";
|
||||
}
|
||||
|
||||
std::string::size_type end = mExtensionString.find_last_not_of(' ');
|
||||
@ -3743,8 +3772,16 @@ GLenum VertexDeclarationCache::applyDeclaration(TranslatedAttribute attributes[]
|
||||
for (int i = 0; i < MAX_VERTEX_ATTRIBS; i++)
|
||||
{
|
||||
if (attributes[i].active)
|
||||
{
|
||||
if (mAppliedVBs[i].serial != attributes[i].serial ||
|
||||
mAppliedVBs[i].stride != attributes[i].stride ||
|
||||
mAppliedVBs[i].offset != attributes[i].offset)
|
||||
{
|
||||
device->SetStreamSource(i, attributes[i].vertexBuffer, attributes[i].offset, attributes[i].stride);
|
||||
mAppliedVBs[i].serial = attributes[i].serial;
|
||||
mAppliedVBs[i].stride = attributes[i].stride;
|
||||
mAppliedVBs[i].offset = attributes[i].offset;
|
||||
}
|
||||
|
||||
element->Stream = i;
|
||||
element->Offset = 0;
|
||||
@ -3765,7 +3802,11 @@ GLenum VertexDeclarationCache::applyDeclaration(TranslatedAttribute attributes[]
|
||||
if (memcmp(entry->cachedElements, elements, (element - elements) * sizeof(D3DVERTEXELEMENT9)) == 0 && entry->vertexDeclaration)
|
||||
{
|
||||
entry->lruCount = ++mMaxLru;
|
||||
if(entry->vertexDeclaration != mLastSetVDecl)
|
||||
{
|
||||
device->SetVertexDeclaration(entry->vertexDeclaration);
|
||||
mLastSetVDecl = entry->vertexDeclaration;
|
||||
}
|
||||
|
||||
return GL_NO_ERROR;
|
||||
}
|
||||
@ -3785,16 +3826,29 @@ GLenum VertexDeclarationCache::applyDeclaration(TranslatedAttribute attributes[]
|
||||
{
|
||||
lastCache->vertexDeclaration->Release();
|
||||
lastCache->vertexDeclaration = NULL;
|
||||
// mLastSetVDecl is set to the replacement, so we don't have to worry
|
||||
// about it.
|
||||
}
|
||||
|
||||
memcpy(lastCache->cachedElements, elements, (element - elements) * sizeof(D3DVERTEXELEMENT9));
|
||||
device->CreateVertexDeclaration(elements, &lastCache->vertexDeclaration);
|
||||
device->SetVertexDeclaration(lastCache->vertexDeclaration);
|
||||
mLastSetVDecl = lastCache->vertexDeclaration;
|
||||
lastCache->lruCount = ++mMaxLru;
|
||||
|
||||
return GL_NO_ERROR;
|
||||
}
|
||||
|
||||
void VertexDeclarationCache::markStateDirty()
|
||||
{
|
||||
for (int i = 0; i < MAX_VERTEX_ATTRIBS; i++)
|
||||
{
|
||||
mAppliedVBs[i].serial = 0;
|
||||
}
|
||||
|
||||
mLastSetVDecl = NULL;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
extern "C"
|
||||
|
@ -230,11 +230,23 @@ class VertexDeclarationCache
|
||||
|
||||
GLenum applyDeclaration(TranslatedAttribute attributes[], Program *program);
|
||||
|
||||
void markStateDirty();
|
||||
|
||||
private:
|
||||
UINT mMaxLru;
|
||||
|
||||
enum { NUM_VERTEX_DECL_CACHE_ENTRIES = 16 };
|
||||
|
||||
struct VBData
|
||||
{
|
||||
unsigned int serial;
|
||||
unsigned int stride;
|
||||
unsigned int offset;
|
||||
};
|
||||
|
||||
VBData mAppliedVBs[MAX_VERTEX_ATTRIBS];
|
||||
IDirect3DVertexDeclaration9 *mLastSetVDecl;
|
||||
|
||||
struct VertexDeclCacheEntry
|
||||
{
|
||||
D3DVERTEXELEMENT9 cachedElements[MAX_VERTEX_ATTRIBS + 1];
|
||||
@ -526,7 +538,12 @@ class Context
|
||||
unsigned int mAppliedRenderTargetSerial;
|
||||
unsigned int mAppliedDepthbufferSerial;
|
||||
unsigned int mAppliedStencilbufferSerial;
|
||||
unsigned int mAppliedIBSerial;
|
||||
bool mDepthStencilInitialized;
|
||||
bool mViewportInitialized;
|
||||
D3DVIEWPORT9 mSetViewport;
|
||||
bool mRenderTargetDescInitialized;
|
||||
D3DSURFACE_DESC mRenderTargetDesc;
|
||||
|
||||
bool mSupportsShaderModel3;
|
||||
bool mSupportsVertexTexture;
|
||||
|
@ -22,6 +22,7 @@ namespace
|
||||
|
||||
namespace gl
|
||||
{
|
||||
unsigned int IndexBuffer::mCurrentSerial = 1;
|
||||
|
||||
IndexDataManager::IndexDataManager(Context *context, IDirect3DDevice9 *device) : mDevice(device)
|
||||
{
|
||||
@ -200,6 +201,7 @@ GLenum IndexDataManager::prepareIndexData(GLenum type, GLsizei count, Buffer *bu
|
||||
}
|
||||
|
||||
translated->indexBuffer = indexBuffer->getBuffer();
|
||||
translated->serial = indexBuffer->getSerial();
|
||||
translated->startIndex = streamOffset / indexSize(format);
|
||||
|
||||
if (buffer)
|
||||
@ -232,6 +234,7 @@ IndexBuffer::IndexBuffer(IDirect3DDevice9 *device, UINT size, D3DFORMAT format)
|
||||
{
|
||||
D3DPOOL pool = getDisplay()->getBufferPool(D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY);
|
||||
HRESULT result = device->CreateIndexBuffer(size, D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY, format, pool, &mIndexBuffer, NULL);
|
||||
mSerial = issueSerial();
|
||||
|
||||
if (FAILED(result))
|
||||
{
|
||||
@ -253,6 +256,16 @@ IDirect3DIndexBuffer9 *IndexBuffer::getBuffer() const
|
||||
return mIndexBuffer;
|
||||
}
|
||||
|
||||
unsigned int IndexBuffer::getSerial() const
|
||||
{
|
||||
return mSerial;
|
||||
}
|
||||
|
||||
unsigned int IndexBuffer::issueSerial()
|
||||
{
|
||||
return mCurrentSerial++;
|
||||
}
|
||||
|
||||
void IndexBuffer::unmap()
|
||||
{
|
||||
if (mIndexBuffer)
|
||||
@ -305,6 +318,7 @@ void StreamingIndexBuffer::reserveSpace(UINT requiredSpace, GLenum type)
|
||||
|
||||
D3DPOOL pool = getDisplay()->getBufferPool(D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY);
|
||||
HRESULT result = mDevice->CreateIndexBuffer(mBufferSize, D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY, type == GL_UNSIGNED_INT ? D3DFMT_INDEX32 : D3DFMT_INDEX16, pool, &mIndexBuffer, NULL);
|
||||
mSerial = issueSerial();
|
||||
|
||||
if (FAILED(result))
|
||||
{
|
||||
@ -358,6 +372,7 @@ void StaticIndexBuffer::reserveSpace(UINT requiredSpace, GLenum type)
|
||||
{
|
||||
D3DPOOL pool = getDisplay()->getBufferPool(D3DUSAGE_WRITEONLY);
|
||||
HRESULT result = mDevice->CreateIndexBuffer(requiredSpace, D3DUSAGE_WRITEONLY, type == GL_UNSIGNED_INT ? D3DFMT_INDEX32 : D3DFMT_INDEX16, pool, &mIndexBuffer, NULL);
|
||||
mSerial = issueSerial();
|
||||
|
||||
if (FAILED(result))
|
||||
{
|
||||
@ -381,24 +396,25 @@ bool StaticIndexBuffer::lookupType(GLenum type)
|
||||
|
||||
UINT StaticIndexBuffer::lookupRange(intptr_t offset, GLsizei count, UINT *minIndex, UINT *maxIndex)
|
||||
{
|
||||
for (unsigned int range = 0; range < mCache.size(); range++)
|
||||
{
|
||||
if (mCache[range].offset == offset && mCache[range].count == count)
|
||||
{
|
||||
*minIndex = mCache[range].minIndex;
|
||||
*maxIndex = mCache[range].maxIndex;
|
||||
IndexRange range = {offset, count};
|
||||
|
||||
return mCache[range].streamOffset;
|
||||
}
|
||||
}
|
||||
std::map<IndexRange, IndexResult>::iterator res = mCache.find(range);
|
||||
|
||||
if (res == mCache.end())
|
||||
{
|
||||
return -1;
|
||||
}
|
||||
|
||||
*minIndex = res->second.minIndex;
|
||||
*maxIndex = res->second.maxIndex;
|
||||
return res->second.streamOffset;
|
||||
}
|
||||
|
||||
void StaticIndexBuffer::addRange(intptr_t offset, GLsizei count, UINT minIndex, UINT maxIndex, UINT streamOffset)
|
||||
{
|
||||
IndexRange indexRange = {offset, count, minIndex, maxIndex, streamOffset};
|
||||
mCache.push_back(indexRange);
|
||||
IndexRange indexRange = {offset, count};
|
||||
IndexResult indexResult = {minIndex, maxIndex, streamOffset};
|
||||
mCache[indexRange] = indexResult;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -28,6 +28,7 @@ struct TranslatedIndexData
|
||||
UINT startIndex;
|
||||
|
||||
IDirect3DIndexBuffer9 *indexBuffer;
|
||||
unsigned int serial;
|
||||
};
|
||||
|
||||
class IndexBuffer
|
||||
@ -42,6 +43,7 @@ class IndexBuffer
|
||||
virtual void reserveSpace(UINT requiredSpace, GLenum type) = 0;
|
||||
|
||||
IDirect3DIndexBuffer9 *getBuffer() const;
|
||||
unsigned int getSerial() const;
|
||||
|
||||
protected:
|
||||
IDirect3DDevice9 *const mDevice;
|
||||
@ -49,6 +51,10 @@ class IndexBuffer
|
||||
IDirect3DIndexBuffer9 *mIndexBuffer;
|
||||
UINT mBufferSize;
|
||||
|
||||
unsigned int mSerial;
|
||||
static unsigned int issueSerial();
|
||||
static unsigned int mCurrentSerial;
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(IndexBuffer);
|
||||
};
|
||||
@ -87,12 +93,28 @@ class StaticIndexBuffer : public IndexBuffer
|
||||
intptr_t offset;
|
||||
GLsizei count;
|
||||
|
||||
bool operator<(const IndexRange& rhs) const
|
||||
{
|
||||
if (offset != rhs.offset)
|
||||
{
|
||||
return offset < rhs.offset;
|
||||
}
|
||||
if (count != rhs.count)
|
||||
{
|
||||
return count < rhs.count;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
struct IndexResult
|
||||
{
|
||||
UINT minIndex;
|
||||
UINT maxIndex;
|
||||
UINT streamOffset;
|
||||
};
|
||||
|
||||
std::vector<IndexRange> mCache;
|
||||
std::map<IndexRange, IndexResult> mCache;
|
||||
};
|
||||
|
||||
class IndexDataManager
|
||||
|
@ -24,6 +24,7 @@
|
||||
namespace gl
|
||||
{
|
||||
unsigned int Program::mCurrentSerial = 1;
|
||||
const char *fakepath = "C:\\fakepath";
|
||||
|
||||
std::string str(int i)
|
||||
{
|
||||
@ -32,7 +33,8 @@ std::string str(int i)
|
||||
return buffer;
|
||||
}
|
||||
|
||||
Uniform::Uniform(GLenum type, const std::string &name, unsigned int arraySize) : type(type), name(name), arraySize(arraySize)
|
||||
Uniform::Uniform(GLenum type, const std::string &_name, unsigned int arraySize)
|
||||
: type(type), _name(_name), name(Program::undecorateUniform(_name)), arraySize(arraySize)
|
||||
{
|
||||
int bytes = UniformTypeSize(type) * arraySize;
|
||||
data = new unsigned char[bytes];
|
||||
@ -46,8 +48,13 @@ Uniform::~Uniform()
|
||||
delete[] data;
|
||||
}
|
||||
|
||||
UniformLocation::UniformLocation(const std::string &name, unsigned int element, unsigned int index)
|
||||
: name(name), element(element), index(index)
|
||||
bool Uniform::isArray()
|
||||
{
|
||||
return _name.compare(0, 3, "ar_") == 0;
|
||||
}
|
||||
|
||||
UniformLocation::UniformLocation(const std::string &_name, unsigned int element, unsigned int index)
|
||||
: name(Program::undecorateUniform(_name)), element(element), index(index)
|
||||
{
|
||||
}
|
||||
|
||||
@ -248,24 +255,23 @@ TextureType Program::getSamplerTextureType(SamplerType type, unsigned int sample
|
||||
return TEXTURE_2D;
|
||||
}
|
||||
|
||||
GLint Program::getUniformLocation(const char *name, bool decorated)
|
||||
GLint Program::getUniformLocation(std::string name)
|
||||
{
|
||||
std::string _name = decorated ? name : decorate(name);
|
||||
int subscript = 0;
|
||||
|
||||
// Strip any trailing array operator and retrieve the subscript
|
||||
size_t open = _name.find_last_of('[');
|
||||
size_t close = _name.find_last_of(']');
|
||||
if (open != std::string::npos && close == _name.length() - 1)
|
||||
size_t open = name.find_last_of('[');
|
||||
size_t close = name.find_last_of(']');
|
||||
if (open != std::string::npos && close == name.length() - 1)
|
||||
{
|
||||
subscript = atoi(_name.substr(open + 1).c_str());
|
||||
_name.erase(open);
|
||||
subscript = atoi(name.substr(open + 1).c_str());
|
||||
name.erase(open);
|
||||
}
|
||||
|
||||
unsigned int numUniforms = mUniformIndex.size();
|
||||
for (unsigned int location = 0; location < numUniforms; location++)
|
||||
{
|
||||
if (mUniformIndex[location].name == _name &&
|
||||
if (mUniformIndex[location].name == name &&
|
||||
mUniformIndex[location].element == subscript)
|
||||
{
|
||||
return location;
|
||||
@ -993,7 +999,7 @@ ID3D10Blob *Program::compileToBinary(const char *hlsl, const char *profile, ID3D
|
||||
|
||||
ID3D10Blob *binary = NULL;
|
||||
ID3D10Blob *errorMessage = NULL;
|
||||
result = D3DCompile(hlsl, strlen(hlsl), NULL, NULL, NULL, "main", profile, flags, 0, &binary, &errorMessage);
|
||||
result = D3DCompile(hlsl, strlen(hlsl), fakepath, NULL, NULL, "main", profile, flags, 0, &binary, &errorMessage);
|
||||
|
||||
if (errorMessage)
|
||||
{
|
||||
@ -1007,7 +1013,6 @@ ID3D10Blob *Program::compileToBinary(const char *hlsl, const char *profile, ID3D
|
||||
errorMessage = NULL;
|
||||
}
|
||||
|
||||
|
||||
if (FAILED(result))
|
||||
{
|
||||
if (result == D3DERR_OUTOFVIDEOMEMORY || result == E_OUTOFMEMORY)
|
||||
@ -1277,7 +1282,7 @@ bool Program::linkVaryings()
|
||||
default: UNREACHABLE();
|
||||
}
|
||||
|
||||
mVertexHLSL += decorate(attribute->name) + " : TEXCOORD" + str(semanticIndex) + ";\n";
|
||||
mVertexHLSL += decorateAttribute(attribute->name) + " : TEXCOORD" + str(semanticIndex) + ";\n";
|
||||
|
||||
semanticIndex += VariableRowCount(attribute->type);
|
||||
}
|
||||
@ -1312,14 +1317,14 @@ bool Program::linkVaryings()
|
||||
|
||||
for (AttributeArray::iterator attribute = mVertexShader->mAttributes.begin(); attribute != mVertexShader->mAttributes.end(); attribute++)
|
||||
{
|
||||
mVertexHLSL += " " + decorate(attribute->name) + " = ";
|
||||
mVertexHLSL += " " + decorateAttribute(attribute->name) + " = ";
|
||||
|
||||
if (VariableRowCount(attribute->type) > 1) // Matrix
|
||||
{
|
||||
mVertexHLSL += "transpose";
|
||||
}
|
||||
|
||||
mVertexHLSL += "(input." + decorate(attribute->name) + ");\n";
|
||||
mVertexHLSL += "(input." + decorateAttribute(attribute->name) + ");\n";
|
||||
}
|
||||
|
||||
mVertexHLSL += "\n"
|
||||
@ -1588,12 +1593,12 @@ void Program::link()
|
||||
|
||||
// these uniforms are searched as already-decorated because gl_ and dx_
|
||||
// are reserved prefixes, and do not receive additional decoration
|
||||
mDxDepthRangeLocation = getUniformLocation("dx_DepthRange", true);
|
||||
mDxDepthLocation = getUniformLocation("dx_Depth", true);
|
||||
mDxViewportLocation = getUniformLocation("dx_Viewport", true);
|
||||
mDxHalfPixelSizeLocation = getUniformLocation("dx_HalfPixelSize", true);
|
||||
mDxFrontCCWLocation = getUniformLocation("dx_FrontCCW", true);
|
||||
mDxPointsOrLinesLocation = getUniformLocation("dx_PointsOrLines", true);
|
||||
mDxDepthRangeLocation = getUniformLocation("dx_DepthRange");
|
||||
mDxDepthLocation = getUniformLocation("dx_Depth");
|
||||
mDxViewportLocation = getUniformLocation("dx_Viewport");
|
||||
mDxHalfPixelSizeLocation = getUniformLocation("dx_HalfPixelSize");
|
||||
mDxFrontCCWLocation = getUniformLocation("dx_FrontCCW");
|
||||
mDxPointsOrLinesLocation = getUniformLocation("dx_PointsOrLines");
|
||||
|
||||
mLinked = true; // Success
|
||||
}
|
||||
@ -1784,9 +1789,9 @@ bool Program::defineUniform(const D3DXHANDLE &constantHandle, const D3DXCONSTANT
|
||||
}
|
||||
}
|
||||
|
||||
bool Program::defineUniform(const D3DXCONSTANT_DESC &constantDescription, std::string &name)
|
||||
bool Program::defineUniform(const D3DXCONSTANT_DESC &constantDescription, std::string &_name)
|
||||
{
|
||||
Uniform *uniform = createUniform(constantDescription, name);
|
||||
Uniform *uniform = createUniform(constantDescription, _name);
|
||||
|
||||
if(!uniform)
|
||||
{
|
||||
@ -1794,7 +1799,7 @@ bool Program::defineUniform(const D3DXCONSTANT_DESC &constantDescription, std::s
|
||||
}
|
||||
|
||||
// Check if already defined
|
||||
GLint location = getUniformLocation(name.c_str(), true);
|
||||
GLint location = getUniformLocation(uniform->name);
|
||||
GLenum type = uniform->type;
|
||||
|
||||
if (location >= 0)
|
||||
@ -1816,13 +1821,13 @@ bool Program::defineUniform(const D3DXCONSTANT_DESC &constantDescription, std::s
|
||||
|
||||
for (unsigned int i = 0; i < uniform->arraySize; ++i)
|
||||
{
|
||||
mUniformIndex.push_back(UniformLocation(name, i, uniformIndex));
|
||||
mUniformIndex.push_back(UniformLocation(_name, i, uniformIndex));
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
Uniform *Program::createUniform(const D3DXCONSTANT_DESC &constantDescription, std::string &name)
|
||||
Uniform *Program::createUniform(const D3DXCONSTANT_DESC &constantDescription, std::string &_name)
|
||||
{
|
||||
if (constantDescription.Rows == 1) // Vectors and scalars
|
||||
{
|
||||
@ -1831,44 +1836,44 @@ Uniform *Program::createUniform(const D3DXCONSTANT_DESC &constantDescription, st
|
||||
case D3DXPT_SAMPLER2D:
|
||||
switch (constantDescription.Columns)
|
||||
{
|
||||
case 1: return new Uniform(GL_SAMPLER_2D, name, constantDescription.Elements);
|
||||
case 1: return new Uniform(GL_SAMPLER_2D, _name, constantDescription.Elements);
|
||||
default: UNREACHABLE();
|
||||
}
|
||||
break;
|
||||
case D3DXPT_SAMPLERCUBE:
|
||||
switch (constantDescription.Columns)
|
||||
{
|
||||
case 1: return new Uniform(GL_SAMPLER_CUBE, name, constantDescription.Elements);
|
||||
case 1: return new Uniform(GL_SAMPLER_CUBE, _name, constantDescription.Elements);
|
||||
default: UNREACHABLE();
|
||||
}
|
||||
break;
|
||||
case D3DXPT_BOOL:
|
||||
switch (constantDescription.Columns)
|
||||
{
|
||||
case 1: return new Uniform(GL_BOOL, name, constantDescription.Elements);
|
||||
case 2: return new Uniform(GL_BOOL_VEC2, name, constantDescription.Elements);
|
||||
case 3: return new Uniform(GL_BOOL_VEC3, name, constantDescription.Elements);
|
||||
case 4: return new Uniform(GL_BOOL_VEC4, name, constantDescription.Elements);
|
||||
case 1: return new Uniform(GL_BOOL, _name, constantDescription.Elements);
|
||||
case 2: return new Uniform(GL_BOOL_VEC2, _name, constantDescription.Elements);
|
||||
case 3: return new Uniform(GL_BOOL_VEC3, _name, constantDescription.Elements);
|
||||
case 4: return new Uniform(GL_BOOL_VEC4, _name, constantDescription.Elements);
|
||||
default: UNREACHABLE();
|
||||
}
|
||||
break;
|
||||
case D3DXPT_INT:
|
||||
switch (constantDescription.Columns)
|
||||
{
|
||||
case 1: return new Uniform(GL_INT, name, constantDescription.Elements);
|
||||
case 2: return new Uniform(GL_INT_VEC2, name, constantDescription.Elements);
|
||||
case 3: return new Uniform(GL_INT_VEC3, name, constantDescription.Elements);
|
||||
case 4: return new Uniform(GL_INT_VEC4, name, constantDescription.Elements);
|
||||
case 1: return new Uniform(GL_INT, _name, constantDescription.Elements);
|
||||
case 2: return new Uniform(GL_INT_VEC2, _name, constantDescription.Elements);
|
||||
case 3: return new Uniform(GL_INT_VEC3, _name, constantDescription.Elements);
|
||||
case 4: return new Uniform(GL_INT_VEC4, _name, constantDescription.Elements);
|
||||
default: UNREACHABLE();
|
||||
}
|
||||
break;
|
||||
case D3DXPT_FLOAT:
|
||||
switch (constantDescription.Columns)
|
||||
{
|
||||
case 1: return new Uniform(GL_FLOAT, name, constantDescription.Elements);
|
||||
case 2: return new Uniform(GL_FLOAT_VEC2, name, constantDescription.Elements);
|
||||
case 3: return new Uniform(GL_FLOAT_VEC3, name, constantDescription.Elements);
|
||||
case 4: return new Uniform(GL_FLOAT_VEC4, name, constantDescription.Elements);
|
||||
case 1: return new Uniform(GL_FLOAT, _name, constantDescription.Elements);
|
||||
case 2: return new Uniform(GL_FLOAT_VEC2, _name, constantDescription.Elements);
|
||||
case 3: return new Uniform(GL_FLOAT_VEC3, _name, constantDescription.Elements);
|
||||
case 4: return new Uniform(GL_FLOAT_VEC4, _name, constantDescription.Elements);
|
||||
default: UNREACHABLE();
|
||||
}
|
||||
break;
|
||||
@ -1883,9 +1888,9 @@ Uniform *Program::createUniform(const D3DXCONSTANT_DESC &constantDescription, st
|
||||
case D3DXPT_FLOAT:
|
||||
switch (constantDescription.Rows)
|
||||
{
|
||||
case 2: return new Uniform(GL_FLOAT_MAT2, name, constantDescription.Elements);
|
||||
case 3: return new Uniform(GL_FLOAT_MAT3, name, constantDescription.Elements);
|
||||
case 4: return new Uniform(GL_FLOAT_MAT4, name, constantDescription.Elements);
|
||||
case 2: return new Uniform(GL_FLOAT_MAT2, _name, constantDescription.Elements);
|
||||
case 3: return new Uniform(GL_FLOAT_MAT3, _name, constantDescription.Elements);
|
||||
case 4: return new Uniform(GL_FLOAT_MAT4, _name, constantDescription.Elements);
|
||||
default: UNREACHABLE();
|
||||
}
|
||||
break;
|
||||
@ -1898,28 +1903,28 @@ Uniform *Program::createUniform(const D3DXCONSTANT_DESC &constantDescription, st
|
||||
}
|
||||
|
||||
// This method needs to match OutputHLSL::decorate
|
||||
std::string Program::decorate(const std::string &string)
|
||||
std::string Program::decorateAttribute(const std::string &name)
|
||||
{
|
||||
if (string.substr(0, 3) != "gl_" && string.substr(0, 3) != "dx_")
|
||||
if (name.compare(0, 3, "gl_") != 0 && name.compare(0, 3, "dx_") != 0)
|
||||
{
|
||||
return "_" + string;
|
||||
}
|
||||
else
|
||||
{
|
||||
return string;
|
||||
return "_" + name;
|
||||
}
|
||||
|
||||
return name;
|
||||
}
|
||||
|
||||
std::string Program::undecorate(const std::string &string)
|
||||
std::string Program::undecorateUniform(const std::string &_name)
|
||||
{
|
||||
if (string.substr(0, 1) == "_")
|
||||
if (_name[0] == '_')
|
||||
{
|
||||
return string.substr(1);
|
||||
return _name.substr(1);
|
||||
}
|
||||
else
|
||||
else if (_name.compare(0, 3, "ar_") == 0)
|
||||
{
|
||||
return string;
|
||||
return _name.substr(3);
|
||||
}
|
||||
|
||||
return _name;
|
||||
}
|
||||
|
||||
bool Program::applyUniform1bv(GLint location, GLsizei count, const GLboolean *v)
|
||||
@ -2448,29 +2453,22 @@ bool Program::applyUniform4iv(GLint location, GLsizei count, const GLint *v)
|
||||
|
||||
|
||||
// append a santized message to the program info log.
|
||||
// The D3D compiler includes the current working directory
|
||||
// in some of the warning or error messages, so lets remove
|
||||
// any occurrances of those that we find in the log.
|
||||
// The D3D compiler includes a fake file path in some of the warning or error
|
||||
// messages, so lets remove all occurrences of this fake file path from the log.
|
||||
void Program::appendToInfoLogSanitized(const char *message)
|
||||
{
|
||||
std::string msg(message);
|
||||
CHAR path[MAX_PATH] = "";
|
||||
size_t len;
|
||||
|
||||
len = GetCurrentDirectoryA(MAX_PATH, path);
|
||||
if (len > 0 && len < MAX_PATH)
|
||||
{
|
||||
size_t found;
|
||||
do {
|
||||
found = msg.find(path);
|
||||
do
|
||||
{
|
||||
found = msg.find(fakepath);
|
||||
if (found != std::string::npos)
|
||||
{
|
||||
// the +1 here is intentional so that we remove
|
||||
// the trailing '\' that occurs after the path
|
||||
msg.erase(found, len+1);
|
||||
msg.erase(found, strlen(fakepath));
|
||||
}
|
||||
} while (found != std::string::npos);
|
||||
}
|
||||
while (found != std::string::npos);
|
||||
|
||||
appendToInfoLog("%s\n", msg.c_str());
|
||||
}
|
||||
@ -2780,7 +2778,7 @@ void Program::getActiveUniform(GLuint index, GLsizei bufsize, GLsizei *length, G
|
||||
unsigned int uniform;
|
||||
for (uniform = 0; uniform < mUniforms.size(); uniform++)
|
||||
{
|
||||
if (mUniforms[uniform]->name.substr(0, 3) == "dx_")
|
||||
if (mUniforms[uniform]->name.compare(0, 3, "dx_") == 0)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
@ -2797,9 +2795,9 @@ void Program::getActiveUniform(GLuint index, GLsizei bufsize, GLsizei *length, G
|
||||
|
||||
if (bufsize > 0)
|
||||
{
|
||||
std::string string = undecorate(mUniforms[uniform]->name);
|
||||
std::string string = mUniforms[uniform]->name;
|
||||
|
||||
if (mUniforms[uniform]->arraySize != 1)
|
||||
if (mUniforms[uniform]->isArray())
|
||||
{
|
||||
string += "[0]";
|
||||
}
|
||||
@ -2825,7 +2823,7 @@ GLint Program::getActiveUniformCount()
|
||||
unsigned int numUniforms = mUniforms.size();
|
||||
for (unsigned int uniformIndex = 0; uniformIndex < numUniforms; uniformIndex++)
|
||||
{
|
||||
if (mUniforms[uniformIndex]->name.substr(0, 3) != "dx_")
|
||||
if (mUniforms[uniformIndex]->name.compare(0, 3, "dx_") != 0)
|
||||
{
|
||||
count++;
|
||||
}
|
||||
@ -2841,10 +2839,10 @@ GLint Program::getActiveUniformMaxLength()
|
||||
unsigned int numUniforms = mUniforms.size();
|
||||
for (unsigned int uniformIndex = 0; uniformIndex < numUniforms; uniformIndex++)
|
||||
{
|
||||
if (!mUniforms[uniformIndex]->name.empty() && mUniforms[uniformIndex]->name.substr(0, 3) != "dx_")
|
||||
if (!mUniforms[uniformIndex]->name.empty() && mUniforms[uniformIndex]->name.compare(0, 3, "dx_") != 0)
|
||||
{
|
||||
int length = (int)(undecorate(mUniforms[uniformIndex]->name).length() + 1);
|
||||
if (mUniforms[uniformIndex]->arraySize != 1)
|
||||
int length = (int)(mUniforms[uniformIndex]->name.length() + 1);
|
||||
if (mUniforms[uniformIndex]->isArray())
|
||||
{
|
||||
length += 3; // Counting in "[0]".
|
||||
}
|
||||
@ -2979,8 +2977,8 @@ void Program::getConstantHandles(Uniform *targetUniform, D3DXHANDLE *constantPS,
|
||||
{
|
||||
if (!targetUniform->handlesSet)
|
||||
{
|
||||
targetUniform->psHandle = mConstantTablePS->GetConstantByName(0, targetUniform->name.c_str());
|
||||
targetUniform->vsHandle = mConstantTableVS->GetConstantByName(0, targetUniform->name.c_str());
|
||||
targetUniform->psHandle = mConstantTablePS->GetConstantByName(0, targetUniform->_name.c_str());
|
||||
targetUniform->vsHandle = mConstantTableVS->GetConstantByName(0, targetUniform->_name.c_str());
|
||||
targetUniform->handlesSet = true;
|
||||
}
|
||||
|
||||
|
@ -1,5 +1,5 @@
|
||||
//
|
||||
// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
|
||||
// Copyright (c) 2002-2011 The ANGLE Project Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
//
|
||||
@ -28,12 +28,15 @@ class VertexShader;
|
||||
// Helper struct representing a single shader uniform
|
||||
struct Uniform
|
||||
{
|
||||
Uniform(GLenum type, const std::string &name, unsigned int arraySize);
|
||||
Uniform(GLenum type, const std::string &_name, unsigned int arraySize);
|
||||
|
||||
~Uniform();
|
||||
|
||||
bool isArray();
|
||||
|
||||
const GLenum type;
|
||||
const std::string name;
|
||||
const std::string _name; // Decorated name
|
||||
const std::string name; // Undecorated name
|
||||
const unsigned int arraySize;
|
||||
|
||||
unsigned char *data;
|
||||
@ -47,7 +50,7 @@ struct Uniform
|
||||
// Struct used for correlating uniforms/elements of uniform arrays to handles
|
||||
struct UniformLocation
|
||||
{
|
||||
UniformLocation(const std::string &name, unsigned int element, unsigned int index);
|
||||
UniformLocation(const std::string &_name, unsigned int element, unsigned int index);
|
||||
|
||||
std::string name;
|
||||
unsigned int element;
|
||||
@ -75,7 +78,7 @@ class Program
|
||||
GLint getSamplerMapping(SamplerType type, unsigned int samplerIndex);
|
||||
TextureType getSamplerTextureType(SamplerType type, unsigned int samplerIndex);
|
||||
|
||||
GLint getUniformLocation(const char *name, bool decorated);
|
||||
GLint getUniformLocation(std::string name);
|
||||
bool setUniform1fv(GLint location, GLsizei count, const GLfloat *v);
|
||||
bool setUniform2fv(GLint location, GLsizei count, const GLfloat *v);
|
||||
bool setUniform3fv(GLint location, GLsizei count, const GLfloat *v);
|
||||
@ -127,6 +130,9 @@ class Program
|
||||
|
||||
unsigned int getSerial() const;
|
||||
|
||||
static std::string decorateAttribute(const std::string &name); // Prepend an underscore
|
||||
static std::string undecorateUniform(const std::string &_name); // Remove leading underscore
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(Program);
|
||||
|
||||
@ -165,9 +171,6 @@ class Program
|
||||
void appendToInfoLog(const char *info, ...);
|
||||
void resetInfoLog();
|
||||
|
||||
static std::string decorate(const std::string &string); // Prepend an underscore
|
||||
static std::string undecorate(const std::string &string); // Remove leading underscore
|
||||
|
||||
static unsigned int issueSerial();
|
||||
|
||||
FragmentShader *mFragmentShader;
|
||||
|
@ -1,5 +1,5 @@
|
||||
//
|
||||
// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
|
||||
// Copyright (c) 2002-2011 The ANGLE Project Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
//
|
||||
@ -21,10 +21,13 @@
|
||||
namespace
|
||||
{
|
||||
enum { INITIAL_STREAM_BUFFER_SIZE = 1024*1024 };
|
||||
// This has to be at least 4k or else it fails on ATI cards.
|
||||
enum { CONSTANT_VERTEX_BUFFER_SIZE = 4096 };
|
||||
}
|
||||
|
||||
namespace gl
|
||||
{
|
||||
unsigned int VertexBuffer::mCurrentSerial = 1;
|
||||
|
||||
VertexDataManager::VertexDataManager(Context *context, IDirect3DDevice9 *device) : mContext(context), mDevice(device)
|
||||
{
|
||||
@ -32,6 +35,7 @@ VertexDataManager::VertexDataManager(Context *context, IDirect3DDevice9 *device)
|
||||
{
|
||||
mDirtyCurrentValue[i] = true;
|
||||
mCurrentValueBuffer[i] = NULL;
|
||||
mCurrentValueOffsets[i] = 0;
|
||||
}
|
||||
|
||||
const D3DCAPS9 &caps = context->getDeviceCaps();
|
||||
@ -234,24 +238,43 @@ GLenum VertexDataManager::prepareVertexData(GLint start, GLsizei count, Translat
|
||||
}
|
||||
|
||||
translated[i].vertexBuffer = vertexBuffer->getBuffer();
|
||||
translated[i].serial = vertexBuffer->getSerial();
|
||||
translated[i].type = converter.d3dDeclType;
|
||||
translated[i].stride = converter.outputElementSize;
|
||||
translated[i].offset = streamOffset;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!mCurrentValueBuffer[i])
|
||||
{
|
||||
mCurrentValueBuffer[i] = new StreamingVertexBuffer(mDevice, CONSTANT_VERTEX_BUFFER_SIZE);
|
||||
}
|
||||
|
||||
StreamingVertexBuffer *buffer = mCurrentValueBuffer[i];
|
||||
|
||||
if (mDirtyCurrentValue[i])
|
||||
{
|
||||
delete mCurrentValueBuffer[i];
|
||||
mCurrentValueBuffer[i] = new ConstantVertexBuffer(mDevice, attribs[i].mCurrentValue[0], attribs[i].mCurrentValue[1], attribs[i].mCurrentValue[2], attribs[i].mCurrentValue[3]);
|
||||
const int requiredSpace = 4 * sizeof(float);
|
||||
buffer->addRequiredSpace(requiredSpace);
|
||||
buffer->reserveRequiredSpace();
|
||||
float *data = static_cast<float*>(buffer->map(VertexAttribute(), requiredSpace, &mCurrentValueOffsets[i]));
|
||||
if (data)
|
||||
{
|
||||
data[0] = attribs[i].mCurrentValue[0];
|
||||
data[1] = attribs[i].mCurrentValue[1];
|
||||
data[2] = attribs[i].mCurrentValue[2];
|
||||
data[3] = attribs[i].mCurrentValue[3];
|
||||
buffer->unmap();
|
||||
mDirtyCurrentValue[i] = false;
|
||||
}
|
||||
}
|
||||
|
||||
translated[i].vertexBuffer = mCurrentValueBuffer[i]->getBuffer();
|
||||
translated[i].serial = mCurrentValueBuffer[i]->getSerial();
|
||||
|
||||
translated[i].type = D3DDECLTYPE_FLOAT4;
|
||||
translated[i].stride = 0;
|
||||
translated[i].offset = 0;
|
||||
translated[i].offset = mCurrentValueOffsets[i];
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -521,6 +544,7 @@ VertexBuffer::VertexBuffer(IDirect3DDevice9 *device, std::size_t size, DWORD usa
|
||||
{
|
||||
D3DPOOL pool = getDisplay()->getBufferPool(usageFlags);
|
||||
HRESULT result = device->CreateVertexBuffer(size, usageFlags, 0, pool, &mVertexBuffer, NULL);
|
||||
mSerial = issueSerial();
|
||||
|
||||
if (FAILED(result))
|
||||
{
|
||||
@ -550,35 +574,14 @@ IDirect3DVertexBuffer9 *VertexBuffer::getBuffer() const
|
||||
return mVertexBuffer;
|
||||
}
|
||||
|
||||
ConstantVertexBuffer::ConstantVertexBuffer(IDirect3DDevice9 *device, float x, float y, float z, float w) : VertexBuffer(device, 4 * sizeof(float), D3DUSAGE_WRITEONLY)
|
||||
unsigned int VertexBuffer::getSerial() const
|
||||
{
|
||||
void *buffer = NULL;
|
||||
|
||||
if (mVertexBuffer)
|
||||
{
|
||||
HRESULT result = mVertexBuffer->Lock(0, 0, &buffer, 0);
|
||||
|
||||
if (FAILED(result))
|
||||
{
|
||||
ERR("Lock failed with error 0x%08x", result);
|
||||
}
|
||||
}
|
||||
|
||||
if (buffer)
|
||||
{
|
||||
float *vector = (float*)buffer;
|
||||
|
||||
vector[0] = x;
|
||||
vector[1] = y;
|
||||
vector[2] = z;
|
||||
vector[3] = w;
|
||||
|
||||
mVertexBuffer->Unlock();
|
||||
}
|
||||
return mSerial;
|
||||
}
|
||||
|
||||
ConstantVertexBuffer::~ConstantVertexBuffer()
|
||||
unsigned int VertexBuffer::issueSerial()
|
||||
{
|
||||
return mCurrentSerial++;
|
||||
}
|
||||
|
||||
ArrayVertexBuffer::ArrayVertexBuffer(IDirect3DDevice9 *device, std::size_t size, DWORD usageFlags) : VertexBuffer(device, size, usageFlags)
|
||||
@ -640,6 +643,7 @@ void StreamingVertexBuffer::reserveRequiredSpace()
|
||||
|
||||
D3DPOOL pool = getDisplay()->getBufferPool(D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY);
|
||||
HRESULT result = mDevice->CreateVertexBuffer(mBufferSize, D3DUSAGE_DYNAMIC | D3DUSAGE_WRITEONLY, 0, pool, &mVertexBuffer, NULL);
|
||||
mSerial = issueSerial();
|
||||
|
||||
if (FAILED(result))
|
||||
{
|
||||
@ -686,7 +690,7 @@ void *StaticVertexBuffer::map(const VertexAttribute &attribute, std::size_t requ
|
||||
}
|
||||
|
||||
int attributeOffset = attribute.mOffset % attribute.stride();
|
||||
VertexElement element = {attribute.mType, attribute.mSize, attribute.mNormalized, attributeOffset, mWritePosition};
|
||||
VertexElement element = {attribute.mType, attribute.mSize, attribute.stride(), attribute.mNormalized, attributeOffset, mWritePosition};
|
||||
mCache.push_back(element);
|
||||
|
||||
*streamOffset = mWritePosition;
|
||||
@ -702,6 +706,7 @@ void StaticVertexBuffer::reserveRequiredSpace()
|
||||
{
|
||||
D3DPOOL pool = getDisplay()->getBufferPool(D3DUSAGE_WRITEONLY);
|
||||
HRESULT result = mDevice->CreateVertexBuffer(mRequiredSpace, D3DUSAGE_WRITEONLY, 0, pool, &mVertexBuffer, NULL);
|
||||
mSerial = issueSerial();
|
||||
|
||||
if (FAILED(result))
|
||||
{
|
||||
@ -723,7 +728,10 @@ std::size_t StaticVertexBuffer::lookupAttribute(const VertexAttribute &attribute
|
||||
{
|
||||
for (unsigned int element = 0; element < mCache.size(); element++)
|
||||
{
|
||||
if (mCache[element].type == attribute.mType && mCache[element].size == attribute.mSize && mCache[element].normalized == attribute.mNormalized)
|
||||
if (mCache[element].type == attribute.mType &&
|
||||
mCache[element].size == attribute.mSize &&
|
||||
mCache[element].stride == attribute.stride() &&
|
||||
mCache[element].normalized == attribute.mNormalized)
|
||||
{
|
||||
if (mCache[element].attributeOffset == attribute.mOffset % attribute.stride())
|
||||
{
|
||||
|
@ -1,5 +1,5 @@
|
||||
//
|
||||
// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
|
||||
// Copyright (c) 2002-2011 The ANGLE Project Authors. All rights reserved.
|
||||
// Use of this source code is governed by a BSD-style license that can be
|
||||
// found in the LICENSE file.
|
||||
//
|
||||
@ -30,6 +30,7 @@ struct TranslatedAttribute
|
||||
UINT stride; // 0 means not to advance the read pointer at all
|
||||
|
||||
IDirect3DVertexBuffer9 *vertexBuffer;
|
||||
unsigned int serial;
|
||||
};
|
||||
|
||||
class VertexBuffer
|
||||
@ -41,22 +42,20 @@ class VertexBuffer
|
||||
void unmap();
|
||||
|
||||
IDirect3DVertexBuffer9 *getBuffer() const;
|
||||
unsigned int getSerial() const;
|
||||
|
||||
protected:
|
||||
IDirect3DDevice9 *const mDevice;
|
||||
IDirect3DVertexBuffer9 *mVertexBuffer;
|
||||
|
||||
unsigned int mSerial;
|
||||
static unsigned int issueSerial();
|
||||
static unsigned int mCurrentSerial;
|
||||
|
||||
private:
|
||||
DISALLOW_COPY_AND_ASSIGN(VertexBuffer);
|
||||
};
|
||||
|
||||
class ConstantVertexBuffer : public VertexBuffer
|
||||
{
|
||||
public:
|
||||
ConstantVertexBuffer(IDirect3DDevice9 *device, float x, float y, float z, float w);
|
||||
~ConstantVertexBuffer();
|
||||
};
|
||||
|
||||
class ArrayVertexBuffer : public VertexBuffer
|
||||
{
|
||||
public:
|
||||
@ -100,6 +99,7 @@ class StaticVertexBuffer : public ArrayVertexBuffer
|
||||
{
|
||||
GLenum type;
|
||||
GLint size;
|
||||
GLsizei stride;
|
||||
bool normalized;
|
||||
int attributeOffset;
|
||||
|
||||
@ -131,7 +131,8 @@ class VertexDataManager
|
||||
StreamingVertexBuffer *mStreamingBuffer;
|
||||
|
||||
bool mDirtyCurrentValue[MAX_VERTEX_ATTRIBS];
|
||||
ConstantVertexBuffer *mCurrentValueBuffer[MAX_VERTEX_ATTRIBS];
|
||||
StreamingVertexBuffer *mCurrentValueBuffer[MAX_VERTEX_ATTRIBS];
|
||||
std::size_t mCurrentValueOffsets[MAX_VERTEX_ATTRIBS];
|
||||
|
||||
// Attribute format conversion
|
||||
struct FormatConverter
|
||||
|
@ -3446,7 +3446,7 @@ int __stdcall glGetUniformLocation(GLuint program, const GLchar* name)
|
||||
return error(GL_INVALID_OPERATION, -1);
|
||||
}
|
||||
|
||||
return programObject->getUniformLocation(name, false);
|
||||
return programObject->getUniformLocation(name);
|
||||
}
|
||||
}
|
||||
catch(std::bad_alloc&)
|
||||
|
@ -7,7 +7,7 @@
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 2 resource.
|
||||
//
|
||||
#include "afxres.h"
|
||||
#include <windows.h>
|
||||
#include "../common/version.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
Loading…
Reference in New Issue
Block a user