diff --git a/opengl/libagl/light.cpp b/opengl/libagl/light.cpp
new file mode 100644
index 0000000..87725cb
--- /dev/null
+++ b/opengl/libagl/light.cpp
@@ -0,0 +1,852 @@
+/* libs/opengles/light.cpp
+**
+** Copyright 2006, The Android Open Source Project
+**
+** Licensed under the Apache License, Version 2.0 (the "License"); 
+** you may not use this file except in compliance with the License. 
+** You may obtain a copy of the License at 
+**
+**     http://www.apache.org/licenses/LICENSE-2.0 
+**
+** Unless required by applicable law or agreed to in writing, software 
+** distributed under the License is distributed on an "AS IS" BASIS, 
+** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 
+** See the License for the specific language governing permissions and 
+** limitations under the License.
+*/
+
+#include <stdio.h>
+#include "context.h"
+#include "fp.h"
+#include "light.h"
+#include "state.h"
+#include "matrix.h"
+
+
+#if defined(__arm__) && defined(__thumb__)
+#warning "light.cpp should not be compiled in thumb on ARM."
+#endif
+
+namespace android {
+
+// ----------------------------------------------------------------------------
+
+static void invalidate_lighting(ogles_context_t* c);
+static void lightVertexValidate(ogles_context_t* c, vertex_t* v);
+static void lightVertexNop(ogles_context_t* c, vertex_t* v);
+static void lightVertex(ogles_context_t* c, vertex_t* v);
+static void lightVertexMaterial(ogles_context_t* c, vertex_t* v);
+
+static inline void vscale3(GLfixed* d, const GLfixed* m, GLfixed s);
+static inline void vsub3w(GLfixed* d, const GLfixed* a, const GLfixed* b);
+
+static __attribute__((noinline))
+void vnorm3(GLfixed* d, const GLfixed* a);
+
+static inline void vsa3(GLfixed* d,
+    const GLfixed* m, GLfixed s, const GLfixed* a);
+static inline void vmla3(GLfixed* d,
+    const GLfixed* m0, const GLfixed* m1, const GLfixed* a);
+static inline void vmul3(GLfixed* d,
+    const GLfixed* m0, const GLfixed* m1);
+
+static GLfixed fog_linear(ogles_context_t* c, GLfixed z);
+static GLfixed fog_exp(ogles_context_t* c, GLfixed z);
+static GLfixed fog_exp2(ogles_context_t* c, GLfixed z);
+
+
+// ----------------------------------------------------------------------------
+
+static void init_white(vec4_t& c) {
+    c.r = c.g = c.b = c.a = 0x10000;
+}
+
+void ogles_init_light(ogles_context_t* c)
+{
+    for (unsigned int i=0 ; i<OGLES_MAX_LIGHTS ; i++) {
+        c->lighting.lights[i].ambient.a = 0x10000;
+        c->lighting.lights[i].position.z = 0x10000;
+        c->lighting.lights[i].spotDir.z = -0x10000;
+        c->lighting.lights[i].spotCutoff = gglIntToFixed(180);
+        c->lighting.lights[i].attenuation[0] = 0x10000;
+    }
+    init_white(c->lighting.lights[0].diffuse);
+    init_white(c->lighting.lights[0].specular);
+
+    c->lighting.front.ambient.r =
+    c->lighting.front.ambient.g =
+    c->lighting.front.ambient.b = gglFloatToFixed(0.2f);
+    c->lighting.front.ambient.a = 0x10000;
+    c->lighting.front.diffuse.r =
+    c->lighting.front.diffuse.g =
+    c->lighting.front.diffuse.b = gglFloatToFixed(0.8f);
+    c->lighting.front.diffuse.a = 0x10000;
+    c->lighting.front.specular.a = 0x10000;
+    c->lighting.front.emission.a = 0x10000;
+
+    c->lighting.lightModel.ambient.r =
+    c->lighting.lightModel.ambient.g =
+    c->lighting.lightModel.ambient.b = gglFloatToFixed(0.2f);
+    c->lighting.lightModel.ambient.a = 0x10000;
+
+    c->lighting.colorMaterial.face = GL_FRONT_AND_BACK;
+    c->lighting.colorMaterial.mode = GL_AMBIENT_AND_DIFFUSE;
+
+    c->fog.mode = GL_EXP;
+    c->fog.fog = fog_exp;
+    c->fog.density = 0x10000;
+    c->fog.end = 0x10000;
+    c->fog.invEndMinusStart = 0x10000;
+
+    invalidate_lighting(c);
+       
+    c->rasterizer.procs.shadeModel(c, GL_SMOOTH);
+    c->lighting.shadeModel = GL_SMOOTH;
+}
+
+void ogles_uninit_light(ogles_context_t* c)
+{
+}
+
+static inline int32_t clampF(GLfixed f) CONST;
+int32_t clampF(GLfixed f) {
+    f = (f & ~(f>>31));
+    if (f >= 0x10000)
+        f = 0x10000;
+    return f;
+}
+
+static GLfixed fog_linear(ogles_context_t* c, GLfixed z) {
+    return clampF(gglMulx((c->fog.end - z), c->fog.invEndMinusStart));
+}
+
+static GLfixed fog_exp(ogles_context_t* c, GLfixed z) {
+    const float e = fixedToFloat(gglMulx(c->fog.density, z));
+    return clampF(gglFloatToFixed(fastexpf(-e)));
+}
+
+static GLfixed fog_exp2(ogles_context_t* c, GLfixed z) {
+    const float e = fixedToFloat(gglMulx(c->fog.density, z));
+    return clampF(gglFloatToFixed(fastexpf(-e*e)));
+}
+
+// ----------------------------------------------------------------------------
+#if 0
+#pragma mark -
+#pragma mark math helpers
+#endif
+
+static inline
+void vscale3(GLfixed* d, const GLfixed* m, GLfixed s) {
+    d[0] = gglMulx(m[0], s);
+    d[1] = gglMulx(m[1], s);
+    d[2] = gglMulx(m[2], s);
+}
+
+static inline
+void vsa3(GLfixed* d, const GLfixed* m, GLfixed s, const GLfixed* a) {
+    d[0] = gglMulAddx(m[0], s, a[0]);
+    d[1] = gglMulAddx(m[1], s, a[1]);
+    d[2] = gglMulAddx(m[2], s, a[2]);
+}
+
+static inline
+void vsub3w(GLfixed* d, const GLfixed* a, const GLfixed* b) {
+    const GLfixed wa = a[3];
+    const GLfixed wb = b[3];
+    if (ggl_likely(wa == wb)) {
+        d[0] = a[0] - b[0];
+        d[1] = a[1] - b[1];
+        d[2] = a[2] - b[2];
+    } else {
+        d[0] = gglMulSubx(a[0], wb, gglMulx(b[0], wa));
+        d[1] = gglMulSubx(a[1], wb, gglMulx(b[1], wa));
+        d[2] = gglMulSubx(a[2], wb, gglMulx(b[2], wa));
+    }
+}
+
+static inline
+void vmla3(GLfixed* d,
+        const GLfixed* m0, const GLfixed* m1, const GLfixed* a)
+{
+    d[0] = gglMulAddx(m0[0], m1[0], a[0]);
+    d[1] = gglMulAddx(m0[1], m1[1], a[1]);
+    d[2] = gglMulAddx(m0[2], m1[2], a[2]);
+}
+
+static inline
+void vmul3(GLfixed* d, const GLfixed* m0, const GLfixed* m1) {
+    d[0] = gglMulx(m0[0], m1[0]);
+    d[1] = gglMulx(m0[1], m1[1]);
+    d[2] = gglMulx(m0[2], m1[2]);
+}
+
+void vnorm3(GLfixed* d, const GLfixed* a)
+{
+    // we must take care of overflows when normalizing a vector
+    GLfixed n;
+    int32_t x = a[0];   x = x>=0 ? x : -x;
+    int32_t y = a[1];   y = y>=0 ? y : -y;
+    int32_t z = a[2];   z = z>=0 ? z : -z;
+    if (ggl_likely(x<=0x6800 && y<=0x6800 && z<= 0x6800)) {
+        // in this case this will all fit on 32 bits
+        n = x*x + y*y + z*z;
+        n = gglSqrtRecipx(n);
+        n <<= 8;
+    } else {
+        // here norm^2 is at least 0x7EC00000 (>>32 == 0.495117)
+        n = vsquare3(x, y, z);
+        n = gglSqrtRecipx(n);
+    }
+    vscale3(d, a, n);
+}
+
+// ----------------------------------------------------------------------------
+#if 0
+#pragma mark -
+#pragma mark lighting equations
+#endif
+
+static inline void light_picker(ogles_context_t* c)
+{
+    if (ggl_likely(!c->lighting.enable)) {
+        c->lighting.lightVertex = lightVertexNop;
+        return;
+    }
+    if (c->lighting.colorMaterial.enable) {
+        c->lighting.lightVertex = lightVertexMaterial;
+    } else {
+        c->lighting.lightVertex = lightVertex;
+    }
+}
+
+static inline void validate_light_mvi(ogles_context_t* c)
+{
+    uint32_t en = c->lighting.enabledLights;
+    while (en) {
+        const int i = 31 - gglClz(en);
+        en &= ~(1<<i);
+        light_t& l = c->lighting.lights[i];
+        c->transforms.mvui.point3(&c->transforms.mvui,
+                &l.objPosition, &l.position);
+        vnorm3(l.normalizedObjPosition.v, l.objPosition.v);
+    }
+}
+
+static inline void validate_light(ogles_context_t* c)
+{
+    // if colorMaterial is enabled, we get the color from the vertex
+    if (!c->lighting.colorMaterial.enable) {
+        material_t& material = c->lighting.front;
+        uint32_t en = c->lighting.enabledLights;
+        while (en) {
+            const int i = 31 - gglClz(en);
+            en &= ~(1<<i);
+            light_t& l = c->lighting.lights[i];
+            vmul3(l.implicitAmbient.v,  material.ambient.v,  l.ambient.v);
+            vmul3(l.implicitDiffuse.v,  material.diffuse.v,  l.diffuse.v);
+            vmul3(l.implicitSpecular.v, material.specular.v, l.specular.v);
+            
+            // this is just a flag to tell if we have a specular component
+            l.implicitSpecular.v[3] =
+                    l.implicitSpecular.r |
+                    l.implicitSpecular.g |
+                    l.implicitSpecular.b;
+            
+            l.rConstAttenuation = (l.attenuation[1] | l.attenuation[2])==0;
+            if (l.rConstAttenuation)
+                l.rConstAttenuation = gglRecipFast(l.attenuation[0]);
+        }
+        // emission and ambient for the whole scene
+        vmla3(  c->lighting.implicitSceneEmissionAndAmbient.v,
+                c->lighting.lightModel.ambient.v,
+                material.ambient.v, 
+                material.emission.v);
+        c->lighting.implicitSceneEmissionAndAmbient.a = material.diffuse.a;
+    }
+    validate_light_mvi(c);
+}
+
+void invalidate_lighting(ogles_context_t* c)
+{
+    // TODO: pick lightVertexValidate or lightVertexValidateMVI
+    // instead of systematically the heavier lightVertexValidate()
+    c->lighting.lightVertex = lightVertexValidate;
+}
+
+void ogles_invalidate_lighting_mvui(ogles_context_t* c)
+{
+    invalidate_lighting(c);
+}
+
+void lightVertexNop(ogles_context_t*, vertex_t* v)
+{
+    // we should never end-up here
+}
+
+void lightVertexValidateMVI(ogles_context_t* c, vertex_t* v)
+{
+    validate_light_mvi(c);
+    light_picker(c);
+    c->lighting.lightVertex(c, v);
+}
+
+void lightVertexValidate(ogles_context_t* c, vertex_t* v)
+{
+    validate_light(c);
+    light_picker(c);
+    c->lighting.lightVertex(c, v);
+}
+
+void lightVertexMaterial(ogles_context_t* c, vertex_t* v)
+{
+    // fetch the material color
+    const GLvoid* cp = c->arrays.color.element(
+            v->index & vertex_cache_t::INDEX_MASK);
+    c->arrays.color.fetch(c, v->color.v, cp);
+
+    // acquire the color-material from the vertex
+    material_t& material = c->lighting.front;
+    material.ambient =
+    material.diffuse = v->color;
+    // implicit arguments need to be computed per/vertex
+    uint32_t en = c->lighting.enabledLights;
+    while (en) {
+        const int i = 31 - gglClz(en);
+        en &= ~(1<<i);
+        light_t& l = c->lighting.lights[i];
+        vmul3(l.implicitAmbient.v,  material.ambient.v,  l.ambient.v);
+        vmul3(l.implicitDiffuse.v,  material.diffuse.v,  l.diffuse.v);
+        vmul3(l.implicitSpecular.v, material.specular.v, l.specular.v);
+    }
+    // emission and ambient for the whole scene
+    vmla3(  c->lighting.implicitSceneEmissionAndAmbient.v,
+            c->lighting.lightModel.ambient.v,
+            material.ambient.v, 
+            material.emission.v);
+    c->lighting.implicitSceneEmissionAndAmbient.a = material.diffuse.a;
+
+    // now we can light our vertex as usual
+    lightVertex(c, v);
+}
+
+void lightVertex(ogles_context_t* c, vertex_t* v)
+{
+    // emission and ambient for the whole scene
+    vec4_t r = c->lighting.implicitSceneEmissionAndAmbient;
+
+    uint32_t en = c->lighting.enabledLights;
+    if (ggl_likely(en)) {
+        // since we do the lighting in object-space, we don't need to
+        // transform each normal. However, we might still have to normalize
+        // it if GL_NORMALIZE is enabled.
+        vec4_t n;
+        c->arrays.normal.fetch(c, n.v,
+            c->arrays.normal.element(v->index & vertex_cache_t::INDEX_MASK));
+        if (c->transforms.rescaleNormals == GL_NORMALIZE)
+            vnorm3(n.v, n.v);
+
+        const material_t& material = c->lighting.front;
+        const int twoSide = c->lighting.lightModel.twoSide;
+
+        while (en) {
+            const int i = 31 - gglClz(en);
+            en &= ~(1<<i);
+            const light_t& l = c->lighting.lights[i];
+            
+            vec4_t d, t;
+            GLfixed s;
+            GLfixed sqDist = 0x10000;
+
+            // compute vertex-to-light vector
+            if (ggl_unlikely(l.position.w)) {
+                vsub3w(d.v, l.objPosition.v, v->obj.v);
+                sqDist = dot3(d.v, d.v);
+                vscale3(d.v, d.v, gglSqrtRecipx(sqDist));
+            } else {
+                // TODO: avoid copy here
+                d = l.normalizedObjPosition;
+            }
+
+            // ambient & diffuse
+            s = dot3(n.v, d.v);
+            s = (s<0) ? (twoSide?(-s):0) : s;
+            vsa3(t.v, l.implicitDiffuse.v, s, l.implicitAmbient.v);
+            
+            // specular
+            if (ggl_unlikely(s && l.implicitSpecular.v[3])) {
+                vec4_t h;
+                h.x = d.x;
+                h.y = d.y;
+                h.z = d.z + 0x10000;
+                vnorm3(h.v, h.v);
+                s = dot3(n.v, h.v);
+                s = (s<0) ? (twoSide?(-s):0) : s;
+                if (s > 0) {
+                    s = gglPowx(s, material.shininess);
+                    vsa3(t.v, l.implicitSpecular.v, s, t.v);
+                }
+            }
+
+            // spot
+            if (ggl_unlikely(l.spotCutoff != gglIntToFixed(180))) {
+                GLfixed spotAtt = -dot3(l.normalizedSpotDir.v, d.v);
+                if (spotAtt >= l.spotCutoffCosine) {
+                    vscale3(t.v, t.v, gglPowx(spotAtt, l.spotExp));
+                }
+            }
+
+            // attenuation
+            if (ggl_unlikely(l.position.w)) {
+                if (l.rConstAttenuation) {
+                    s = l.rConstAttenuation;
+                } else {
+                    s = gglMulAddx(sqDist, l.attenuation[2], l.attenuation[0]);
+                    if (l.attenuation[1])
+                        s = gglMulAddx(gglSqrtx(sqDist), l.attenuation[1], s);
+                    s = gglRecipFast(s);
+                }
+                vscale3(t.v, t.v, s);
+            }
+
+            r.r += t.r;
+            r.g += t.g;
+            r.b += t.b;
+        }
+    }
+    v->color.r = gglClampx(r.r);
+    v->color.g = gglClampx(r.g);
+    v->color.b = gglClampx(r.b);
+    v->color.a = gglClampx(r.a);
+    v->flags |= vertex_t::LIT;
+}
+
+static void lightModelx(GLenum pname, GLfixed param, ogles_context_t* c)
+{
+    if (ggl_unlikely(pname != GL_LIGHT_MODEL_TWO_SIDE)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    c->lighting.lightModel.twoSide = param ? GL_TRUE : GL_FALSE;
+    invalidate_lighting(c);
+}
+
+static void lightx(GLenum i, GLenum pname, GLfixed param, ogles_context_t* c)
+{
+    if (ggl_unlikely(uint32_t(i-GL_LIGHT0) >= OGLES_MAX_LIGHTS)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+
+    light_t& light = c->lighting.lights[i-GL_LIGHT0];
+    const GLfixed kDegToRad = GLfixed((M_PI * gglIntToFixed(1)) / 180.0f);
+    switch (pname) {
+    case GL_SPOT_EXPONENT:
+        if (GGLfixed(param) >= gglIntToFixed(128)) {
+            ogles_error(c, GL_INVALID_VALUE);
+            return;
+        }
+        light.spotExp = param;
+        break;
+    case GL_SPOT_CUTOFF:
+        if (param!=gglIntToFixed(180) && GGLfixed(param)>=gglIntToFixed(90)) {
+            ogles_error(c, GL_INVALID_VALUE);
+            return;
+        }
+        light.spotCutoff = param;
+        light.spotCutoffCosine = 
+                gglFloatToFixed(cosinef((M_PI/(180.0f*65536.0f))*param));
+        break;
+    case GL_CONSTANT_ATTENUATION:
+        if (param < 0) {
+            ogles_error(c, GL_INVALID_VALUE);
+            return;
+        }
+        light.attenuation[0] = param;
+        break;
+    case GL_LINEAR_ATTENUATION:
+        if (param < 0) {
+            ogles_error(c, GL_INVALID_VALUE);
+            return;
+        }
+        light.attenuation[1] = param;
+        break;
+    case GL_QUADRATIC_ATTENUATION:
+        if (param < 0) {
+            ogles_error(c, GL_INVALID_VALUE);
+            return;
+        }
+        light.attenuation[2] = param;
+        break;
+    default:
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    invalidate_lighting(c);
+}
+
+static void lightxv(GLenum i, GLenum pname, const GLfixed *params, ogles_context_t* c)
+{
+    if (ggl_unlikely(uint32_t(i-GL_LIGHT0) >= OGLES_MAX_LIGHTS)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+
+    GLfixed* what;
+    light_t& light = c->lighting.lights[i-GL_LIGHT0];
+    switch (pname) {
+    case GL_AMBIENT:
+        what = light.ambient.v;
+        break;
+    case GL_DIFFUSE:
+        what = light.diffuse.v;
+        break;
+    case GL_SPECULAR:
+        what = light.specular.v;
+        break;
+    case GL_POSITION: {
+        ogles_validate_transform(c, transform_state_t::MODELVIEW);
+        transform_t& mv = c->transforms.modelview.transform;
+        memcpy(light.position.v, params, sizeof(light.position.v));
+        mv.point4(&mv, &light.position, &light.position);
+        invalidate_lighting(c);
+        return;
+    }
+    case GL_SPOT_DIRECTION: {
+        ogles_validate_transform(c, transform_state_t::MVUI);
+        transform_t& mvui = c->transforms.mvui;
+        mvui.point3(&mvui, &light.spotDir, (vec4_t*)params);
+        vnorm3(light.normalizedSpotDir.v, light.spotDir.v);
+        invalidate_lighting(c);
+        return;
+    }
+    default:
+        lightx(i, pname, params[0], c);
+        return;
+    }
+    what[0] = params[0];
+    what[1] = params[1];
+    what[2] = params[2];
+    what[3] = params[3];
+    invalidate_lighting(c);
+}
+
+static void materialx(GLenum face, GLenum pname, GLfixed param, ogles_context_t* c)
+{
+    if (ggl_unlikely(face != GL_FRONT_AND_BACK)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    if (ggl_unlikely(pname != GL_SHININESS)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    c->lighting.front.shininess = param;
+    invalidate_lighting(c);
+}
+
+static void fogx(GLenum pname, GLfixed param, ogles_context_t* c)
+{
+    switch (pname) {
+    case GL_FOG_DENSITY:
+        if (param >= 0) {
+            c->fog.density = param;
+            break;
+        }
+        ogles_error(c, GL_INVALID_VALUE);
+        break;
+    case GL_FOG_START:
+        c->fog.start = gglClampx(param);
+        c->fog.invEndMinusStart = gglRecip(c->fog.end - c->fog.start);
+        break;
+    case GL_FOG_END:
+        c->fog.end = gglClampx(param);
+        c->fog.invEndMinusStart = gglRecip(c->fog.end - c->fog.start);
+        break;
+    case GL_FOG_MODE:
+        switch (param) {
+        case GL_LINEAR:
+            c->fog.mode = param;
+            c->fog.fog = fog_linear;
+            break;
+        case GL_EXP:
+            c->fog.mode = param;
+            c->fog.fog = fog_exp;
+            break;
+        case GL_EXP2:
+            c->fog.mode = param;
+            c->fog.fog = fog_exp2;
+            break;
+        default:
+            ogles_error(c, GL_INVALID_ENUM);
+            break;
+        }
+        break;
+    default:
+        ogles_error(c, GL_INVALID_ENUM);
+        break;
+    }
+}
+
+// ----------------------------------------------------------------------------
+}; // namespace android
+// ----------------------------------------------------------------------------
+
+using namespace android;
+
+#if 0
+#pragma mark -
+#pragma mark lighting APIs
+#endif
+
+void glShadeModel(GLenum mode)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    if (ggl_unlikely(mode != GL_SMOOTH && mode != GL_FLAT)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    c->lighting.shadeModel = mode;
+}
+
+void glLightModelf(GLenum pname, GLfloat param)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    lightModelx(pname, gglFloatToFixed(param), c);
+}
+
+void glLightModelx(GLenum pname, GLfixed param)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    lightModelx(pname, param, c);
+}
+
+void glLightModelfv(GLenum pname, const GLfloat *params)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    if (pname == GL_LIGHT_MODEL_TWO_SIDE) {
+        lightModelx(pname, gglFloatToFixed(params[0]), c);
+        return;
+    }
+
+    if (ggl_unlikely(pname != GL_LIGHT_MODEL_AMBIENT)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+
+    c->lighting.lightModel.ambient.r = gglFloatToFixed(params[0]);
+    c->lighting.lightModel.ambient.g = gglFloatToFixed(params[1]);
+    c->lighting.lightModel.ambient.b = gglFloatToFixed(params[2]);
+    c->lighting.lightModel.ambient.a = gglFloatToFixed(params[3]);
+    invalidate_lighting(c);
+}
+
+void glLightModelxv(GLenum pname, const GLfixed *params)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    if (pname == GL_LIGHT_MODEL_TWO_SIDE) {
+        lightModelx(pname, params[0], c);
+        return;
+    }
+
+    if (ggl_unlikely(pname != GL_LIGHT_MODEL_AMBIENT)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+
+    c->lighting.lightModel.ambient.r = params[0];
+    c->lighting.lightModel.ambient.g = params[1];
+    c->lighting.lightModel.ambient.b = params[2];
+    c->lighting.lightModel.ambient.a = params[3];
+    invalidate_lighting(c);
+}
+
+// ----------------------------------------------------------------------------
+#if 0
+#pragma mark -
+#endif
+
+void glLightf(GLenum i, GLenum pname, GLfloat param)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    lightx(i, pname, gglFloatToFixed(param), c);
+}
+
+void glLightx(GLenum i, GLenum pname, GLfixed param)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    lightx(i, pname, param, c);
+}
+
+void glLightfv(GLenum i, GLenum pname, const GLfloat *params)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    switch (pname) {
+    case GL_SPOT_EXPONENT:
+    case GL_SPOT_CUTOFF:
+    case GL_CONSTANT_ATTENUATION:
+    case GL_LINEAR_ATTENUATION:
+    case GL_QUADRATIC_ATTENUATION:
+        lightx(i, pname, gglFloatToFixed(params[0]), c);
+        return;
+    }
+
+    GLfixed paramsx[4];
+    paramsx[0] = gglFloatToFixed(params[0]);
+    paramsx[1] = gglFloatToFixed(params[1]);
+    paramsx[2] = gglFloatToFixed(params[2]);
+    if (pname != GL_SPOT_DIRECTION)
+        paramsx[3] = gglFloatToFixed(params[3]);
+
+    lightxv(i, pname, paramsx, c);
+}
+
+void glLightxv(GLenum i, GLenum pname, const GLfixed *params)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    lightxv(i, pname, params, c);
+}
+
+// ----------------------------------------------------------------------------
+#if 0
+#pragma mark -
+#endif
+
+void glMaterialf(GLenum face, GLenum pname, GLfloat param)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    materialx(face, pname, gglFloatToFixed(param), c);
+}
+
+void glMaterialx(GLenum face, GLenum pname, GLfixed param)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    materialx(face, pname, param, c);
+}
+
+void glMaterialfv(
+    GLenum face, GLenum pname, const GLfloat *params)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    if (ggl_unlikely(face != GL_FRONT_AND_BACK)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    GLfixed* what=0;
+    GLfixed* other=0;
+    switch (pname) {
+    case GL_AMBIENT:    what = c->lighting.front.ambient.v; break;
+    case GL_DIFFUSE:    what = c->lighting.front.diffuse.v; break;
+    case GL_SPECULAR:   what = c->lighting.front.specular.v; break;
+    case GL_EMISSION:   what = c->lighting.front.emission.v; break;
+    case GL_AMBIENT_AND_DIFFUSE:
+        what  = c->lighting.front.ambient.v; break;
+        other = c->lighting.front.diffuse.v; break;
+        break;
+    case GL_SHININESS:
+        c->lighting.front.shininess = gglFloatToFixed(params[0]);
+        invalidate_lighting(c);
+        return;
+    default:
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    what[0] = gglFloatToFixed(params[0]);
+    what[1] = gglFloatToFixed(params[1]);
+    what[2] = gglFloatToFixed(params[2]);
+    what[3] = gglFloatToFixed(params[3]);
+    if (other) {
+        other[0] = what[0];
+        other[1] = what[1];
+        other[2] = what[2];
+        other[3] = what[3];
+    }
+    invalidate_lighting(c);
+}
+
+void glMaterialxv(
+    GLenum face, GLenum pname, const GLfixed *params)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    if (ggl_unlikely(face != GL_FRONT_AND_BACK)) {
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    GLfixed* what=0;
+    GLfixed* other=0;
+    switch (pname) {
+    case GL_AMBIENT:    what = c->lighting.front.ambient.v; break;
+    case GL_DIFFUSE:    what = c->lighting.front.diffuse.v; break;
+    case GL_SPECULAR:   what = c->lighting.front.specular.v; break;
+    case GL_EMISSION:   what = c->lighting.front.emission.v; break;
+    case GL_AMBIENT_AND_DIFFUSE:
+        what = c->lighting.front.ambient.v; break;
+        other= c->lighting.front.diffuse.v; break;
+        break;
+    case GL_SHININESS:
+        c->lighting.front.shininess = gglFloatToFixed(params[0]);
+        invalidate_lighting(c);
+        return;
+    default:
+        ogles_error(c, GL_INVALID_ENUM);
+        return;
+    }
+    what[0] = params[0];
+    what[1] = params[1];
+    what[2] = params[2];
+    what[3] = params[3];
+    if (other) {
+        other[0] = what[0];
+        other[1] = what[1];
+        other[2] = what[2];
+        other[3] = what[3];
+    }
+    invalidate_lighting(c);
+}
+
+// ----------------------------------------------------------------------------
+#if 0
+#pragma mark -
+#pragma mark fog
+#endif
+
+void glFogf(GLenum pname, GLfloat param) {
+    ogles_context_t* c = ogles_context_t::get();
+    GLfixed paramx = (GLfixed)param;
+    if (pname != GL_FOG_MODE)
+        paramx = gglFloatToFixed(param);
+    fogx(pname, paramx, c);
+}
+
+void glFogx(GLenum pname, GLfixed param) {
+    ogles_context_t* c = ogles_context_t::get();
+    fogx(pname, param, c);
+}
+
+void glFogfv(GLenum pname, const GLfloat *params)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    if (pname != GL_FOG_COLOR) {
+        GLfixed paramx = (GLfixed)params[0];
+        if (pname != GL_FOG_MODE)
+            paramx = gglFloatToFixed(params[0]);
+        fogx(pname, paramx, c);
+        return;
+    }
+    GLfixed paramsx[4];
+    paramsx[0] = gglFloatToFixed(params[0]);
+    paramsx[1] = gglFloatToFixed(params[1]);
+    paramsx[2] = gglFloatToFixed(params[2]);
+    paramsx[3] = gglFloatToFixed(params[3]);
+    c->rasterizer.procs.fogColor3xv(c, paramsx);
+}
+
+void glFogxv(GLenum pname, const GLfixed *params)
+{
+    ogles_context_t* c = ogles_context_t::get();
+    if (pname != GL_FOG_COLOR) {
+        fogx(pname, params[0], c);
+        return;
+    }
+    c->rasterizer.procs.fogColor3xv(c, params);
+}
