Program: 163702
Project: 163702
Buggy source:
protected void renderTriangles(int start,int stop){
  report("String_Node_Str");
  int numTextures=0;
  gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
  gl.glEnableClientState(GL10.GL_COLOR_ARRAY);
  gl.glEnableClientState(GL10.GL_NORMAL_ARRAY);
  for (int j=start; j < stop; j++) {
    int i=faceOffset[j];
    PImage[] images=faceTextures[j];
    if (1 < numMultitextures) {
      for (int t=0; t < numMultitextures; t++) {
        if (images[t] != null) {
          PTexture tex=images[t].getTexture();
          if (tex == null) {
            tex=images[t].createTexture();
            if (tex == null) {
              break;
            }
          }
          gl.glEnable(tex.getGLTarget());
          gl.glActiveTexture(GL10.GL_TEXTURE0 + t);
          gl.glBindTexture(tex.getGLTarget(),tex.getGLID());
          renderTextures[numTextures]=tex;
          numTextures++;
        }
 else {
          break;
        }
      }
    }
 else     if (images[0] != null) {
      PTexture tex=images[0].getTexture();
      if (tex == null) {
        tex=images[0].createTexture();
      }
      if (tex != null) {
        gl.glEnable(tex.getGLTarget());
        gl.glActiveTexture(GL10.GL_TEXTURE0);
        gl.glBindTexture(tex.getGLTarget(),tex.getGLID());
        renderTextures[0]=tex;
        numTextures=1;
      }
    }
    if (0 < numTextures) {
      if (numTexBuffers < numTextures) {
        addTexBuffers(numTextures - numTexBuffers);
      }
      gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
      if (1 < numTextures) {
        setMultitextureBlend(renderTextures,numTextures);
      }
    }
    if (recordingShape) {
      numRecordedTextures=PApplet.max(numRecordedTextures,numTextures);
      int n0=recordedVertices.size();
      int n1=n0 + 3 * faceLength[j] - 1;
      PShape3D child=(PShape3D)PShape3D.createChild("String_Node_Str" + recordedChildren.size(),n0,n1,TRIANGLES,0,images);
      recordedChildren.add(child);
    }
    int size=3 * faceLength[j];
    while (vertexBuffer.capacity() / 3 < size) {
      expandBuffers();
    }
    vertexBuffer.position(0);
    colorBuffer.position(0);
    normalBuffer.position(0);
    for (int t=0; t < numTextures; t++) {
      texCoordBuffer[t].position(0);
    }
    int n=0;
    for (int k=0; k < faceLength[j]; k++) {
      int na=triangles[i][VERTEX1];
      int nb=triangles[i][VERTEX2];
      int nc=triangles[i][VERTEX3];
      float a[]=vertices[na];
      float b[]=vertices[nb];
      float c[]=vertices[nc];
      if (autoNormal && (a[HAS_NORMAL] == 0 || b[HAS_NORMAL] == 0 || c[HAS_NORMAL] == 0)) {
        float x1=b[X] - a[X];
        float y1=b[Y] - a[Y];
        float z1=b[Z] - a[Z];
        float x2=b[X] - c[X];
        float y2=b[Y] - c[Y];
        float z2=b[Z] - c[Z];
        float cx=y1 * z2 - y2 * z1;
        float cy=z1 * x2 - z2 * x1;
        float cz=x1 * y2 - x2 * y1;
        float norm=PApplet.sqrt(cx * cx + cy * cy + cz * cz);
        cx/=norm;
        cy/=norm;
        cz/=norm;
        a[NX]=b[NX]=c[NX]=cx;
        a[NY]=b[NY]=c[NY]=cy;
        a[NZ]=b[NZ]=c[NZ]=cz;
        a[HAS_NORMAL]=b[HAS_NORMAL]=c[HAS_NORMAL]=1;
      }
      if (numTextures == 1) {
        float uscale=1.0f;
        float vscale=1.0f;
        float cx=0.0f;
        float sx=+1.0f;
        float cy=0.0f;
        float sy=+1.0f;
        PTexture tex=renderTextures[0];
        uscale*=tex.getMaxTexCoordU();
        vscale*=tex.getMaxTexCoordV();
        if (tex.isFlippedX()) {
          cx=1.0f;
          sx=-1.0f;
        }
        if (tex.isFlippedY()) {
          cy=1.0f;
          sy=-1.0f;
        }
        renderUa[0]=(cx + sx * a[U]) * uscale;
        renderVa[0]=(cy + sy * a[V]) * vscale;
        renderUb[0]=(cx + sx * b[U]) * uscale;
        renderVb[0]=(cy + sy * b[V]) * vscale;
        renderUc[0]=(cx + sx * c[U]) * uscale;
        renderVc[0]=(cy + sy * c[V]) * vscale;
      }
 else       if (1 < numTextures) {
        for (int t=0; t < numTextures; t++) {
          float uscale=1.0f;
          float vscale=1.0f;
          float cx=0.0f;
          float sx=+1.0f;
          float cy=0.0f;
          float sy=+1.0f;
          PTexture tex=renderTextures[t];
          uscale*=tex.getMaxTexCoordU();
          vscale*=tex.getMaxTexCoordV();
          if (tex.isFlippedX()) {
            cx=1.0f;
            sx=-1.0f;
          }
          if (tex.isFlippedY()) {
            cy=1.0f;
            sy=-1.0f;
          }
          renderUa[t]=(cx + sx * vertexU[na][t]) * uscale;
          renderVa[t]=(cy + sy * vertexV[na][t]) * vscale;
          renderUb[t]=(cx + sx * vertexU[nb][t]) * uscale;
          renderVb[t]=(cy + sy * vertexV[nb][t]) * vscale;
          renderUc[t]=(cx + sx * vertexU[nc][t]) * uscale;
          renderVc[t]=(cy + sy * vertexV[nc][t]) * vscale;
        }
      }
      if (recordingShape) {
        recordedVertices.add(new PVector(a[X],a[Y],a[Z]));
        recordedColors.add(new float[]{a[R],a[G],a[B],a[A]});
        recordedNormals.add(new PVector(a[NX],a[NY],a[NZ]));
        for (int t=0; t < numTextures; t++) {
          recordedTexCoords[t].add(new PVector(renderUa[t],renderVa[t],0.0f));
        }
        for (int t=numTextures; t < maxTextureUnits; t++) {
          recordedTexCoords[t].add(new PVector(0.0f,0.0f,0.0f));
        }
      }
 else {
        vertexArray[3 * n + 0]=toFixed32(a[X]);
        vertexArray[3 * n + 1]=toFixed32(a[Y]);
        vertexArray[3 * n + 2]=toFixed32(a[Z]);
        colorArray[4 * n + 0]=toFixed32(a[R]);
        colorArray[4 * n + 1]=toFixed32(a[G]);
        colorArray[4 * n + 2]=toFixed32(a[B]);
        colorArray[4 * n + 3]=toFixed32(a[A]);
        normalArray[3 * n + 0]=toFixed32(a[NX]);
        normalArray[3 * n + 1]=toFixed32(a[NY]);
        normalArray[3 * n + 2]=toFixed32(a[NZ]);
        for (int t=0; t < numTextures; t++) {
          texCoordArray[t][2 * n + 0]=toFixed32(renderUa[t]);
          texCoordArray[t][2 * n + 1]=toFixed32(renderVa[t]);
        }
        n++;
      }
      if (recordingShape) {
        recordedVertices.add(new PVector(b[X],b[Y],b[Z]));
        recordedColors.add(new float[]{b[R],b[G],b[B],b[A]});
        recordedNormals.add(new PVector(b[NX],b[NY],b[NZ]));
        for (int t=0; t < numTextures; t++) {
          recordedTexCoords[t].add(new PVector(renderUb[t],renderVb[t],0.0f));
        }
        for (int t=numTextures; t < maxTextureUnits; t++) {
          recordedTexCoords[t].add(new PVector(0.0f,0.0f,0.0f));
        }
      }
 else {
        vertexArray[3 * n + 0]=toFixed32(b[X]);
        vertexArray[3 * n + 1]=toFixed32(b[Y]);
        vertexArray[3 * n + 2]=toFixed32(b[Z]);
        colorArray[4 * n + 0]=toFixed32(b[R]);
        colorArray[4 * n + 1]=toFixed32(b[G]);
        colorArray[4 * n + 2]=toFixed32(b[B]);
        colorArray[4 * n + 3]=toFixed32(b[A]);
        normalArray[3 * n + 0]=toFixed32(b[NX]);
        normalArray[3 * n + 1]=toFixed32(b[NY]);
        normalArray[3 * n + 2]=toFixed32(b[NZ]);
        for (int t=0; t < numTextures; t++) {
          texCoordArray[t][2 * n + 0]=toFixed32(renderUb[t]);
          texCoordArray[t][2 * n + 1]=toFixed32(renderVb[t]);
        }
        n++;
      }
      if (recordingShape) {
        recordedVertices.add(new PVector(c[X],c[Y],c[Z]));
        recordedColors.add(new float[]{c[R],c[G],c[B],c[A]});
        recordedNormals.add(new PVector(c[NX],c[NY],c[NZ]));
        for (int t=0; t < numTextures; t++) {
          recordedTexCoords[t].add(new PVector(renderUc[t],renderVc[t],0.0f));
        }
        for (int t=numTextures; t < maxTextureUnits; t++) {
          recordedTexCoords[t].add(new PVector(0.0f,0.0f,0.0f));
        }
      }
 else {
        vertexArray[3 * n + 0]=toFixed32(c[X]);
        vertexArray[3 * n + 1]=toFixed32(c[Y]);
        vertexArray[3 * n + 2]=toFixed32(c[Z]);
        colorArray[4 * n + 0]=toFixed32(c[R]);
        colorArray[4 * n + 1]=toFixed32(c[G]);
        colorArray[4 * n + 2]=toFixed32(c[B]);
        colorArray[4 * n + 3]=toFixed32(c[A]);
        normalArray[3 * n + 0]=toFixed32(c[NX]);
        normalArray[3 * n + 1]=toFixed32(c[NY]);
        normalArray[3 * n + 2]=toFixed32(c[NZ]);
        for (int t=0; t < numTextures; t++) {
          texCoordArray[t][2 * n + 0]=toFixed32(renderUc[t]);
          texCoordArray[t][2 * n + 1]=toFixed32(renderVc[t]);
        }
        n++;
      }
      i++;
    }
    if (!recordingShape) {
      vertexBuffer.put(vertexArray);
      colorBuffer.put(colorArray);
      normalBuffer.put(normalArray);
      for (int t=0; t < numTextures; t++) {
        texCoordBuffer[t].put(texCoordArray[t]);
      }
      vertexBuffer.position(0);
      colorBuffer.position(0);
      normalBuffer.position(0);
      for (int t=0; t < numTextures; t++) {
        texCoordBuffer[t].position(0);
      }
      gl.glVertexPointer(3,GL10.GL_FIXED,0,vertexBuffer);
      gl.glColorPointer(4,GL10.GL_FIXED,0,colorBuffer);
      gl.glNormalPointer(GL10.GL_FIXED,0,normalBuffer);
      for (int t=0; t < numTextures; t++) {
        gl.glClientActiveTexture(GL10.GL_TEXTURE0 + t);
        gl.glTexCoordPointer(2,GL10.GL_FIXED,0,texCoordBuffer[t]);
      }
      gl.glDrawArrays(GL10.GL_TRIANGLES,0,3 * faceLength[j]);
    }
    if (0 < numTextures) {
      if (1 < numTextures) {
        clearMultitextureBlend(numTextures);
      }
      for (int t=0; t < numTextures; t++) {
        PTexture tex=renderTextures[t];
        gl.glDisable(tex.getGLTarget());
      }
      gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
    }
  }
  gl.glDisableClientState(GL10.GL_NORMAL_ARRAY);
  gl.glDisableClientState(GL10.GL_COLOR_ARRAY);
  gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
  report("String_Node_Str");
}

Fixed version (ground truth):
protected void renderTriangles(int start,int stop){
  report("String_Node_Str");
  int numTextures=0;
  gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
  gl.glEnableClientState(GL10.GL_COLOR_ARRAY);
  gl.glEnableClientState(GL10.GL_NORMAL_ARRAY);
  for (int j=start; j < stop; j++) {
    int i=faceOffset[j];
    PImage[] images=faceTextures[j];
    if (1 < numMultitextures) {
      for (int t=0; t < numMultitextures; t++) {
        if (images[t] != null) {
          PTexture tex=images[t].getTexture();
          if (tex == null) {
            tex=images[t].createTexture();
            if (tex == null) {
              break;
            }
          }
          gl.glEnable(tex.getGLTarget());
          gl.glActiveTexture(GL10.GL_TEXTURE0 + t);
          gl.glBindTexture(tex.getGLTarget(),tex.getGLID());
          renderTextures[numTextures]=tex;
          numTextures++;
        }
 else {
          break;
        }
      }
    }
 else     if (images[0] != null) {
      PTexture tex=images[0].getTexture();
      if (tex == null) {
        tex=images[0].createTexture();
      }
      if (tex != null) {
        gl.glEnable(tex.getGLTarget());
        gl.glActiveTexture(GL10.GL_TEXTURE0);
        gl.glBindTexture(tex.getGLTarget(),tex.getGLID());
        renderTextures[0]=tex;
        numTextures=1;
      }
    }
    if (0 < numTextures) {
      if (numTexBuffers < numTextures) {
        addTexBuffers(numTextures - numTexBuffers);
      }
      gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
      if (1 < numTextures) {
        setMultitextureBlend(renderTextures,numTextures);
      }
    }
    if (recordingShape) {
      numRecordedTextures=PApplet.max(numRecordedTextures,numTextures);
      int n0=recordedVertices.size();
      int n1=n0 + 3 * faceLength[j] - 1;
      PShape3D child=(PShape3D)PShape3D.createChild("String_Node_Str" + recordedChildren.size(),n0,n1,TRIANGLES,0,images);
      recordedChildren.add(child);
    }
    int size=3 * faceLength[j];
    while (vertexBuffer.capacity() / 3 < size) {
      expandBuffers();
    }
    vertexBuffer.position(0);
    colorBuffer.position(0);
    normalBuffer.position(0);
    for (int t=0; t < numTextures; t++) {
      texCoordBuffer[t].position(0);
    }
    int n=0;
    for (int k=0; k < faceLength[j]; k++) {
      int na=triangles[i][VERTEX1];
      int nb=triangles[i][VERTEX2];
      int nc=triangles[i][VERTEX3];
      float a[]=vertices[na];
      float b[]=vertices[nb];
      float c[]=vertices[nc];
      if (autoNormal && (a[HAS_NORMAL] == 0 || b[HAS_NORMAL] == 0 || c[HAS_NORMAL] == 0)) {
        float x1=b[X] - a[X];
        float y1=b[Y] - a[Y];
        float z1=b[Z] - a[Z];
        float x2=b[X] - c[X];
        float y2=b[Y] - c[Y];
        float z2=b[Z] - c[Z];
        float cx=y1 * z2 - y2 * z1;
        float cy=z1 * x2 - z2 * x1;
        float cz=x1 * y2 - x2 * y1;
        float norm=PApplet.sqrt(cx * cx + cy * cy + cz * cz);
        cx/=norm;
        cy/=norm;
        cz/=norm;
        a[NX]=b[NX]=c[NX]=cx;
        a[NY]=b[NY]=c[NY]=cy;
        a[NZ]=b[NZ]=c[NZ]=cz;
        a[HAS_NORMAL]=b[HAS_NORMAL]=c[HAS_NORMAL]=1;
      }
      if (numTextures == 1) {
        float uscale=1.0f;
        float vscale=1.0f;
        float cx=0.0f;
        float sx=+1.0f;
        float cy=0.0f;
        float sy=+1.0f;
        PTexture tex=renderTextures[0];
        uscale*=tex.getMaxTexCoordU();
        vscale*=tex.getMaxTexCoordV();
        if (tex.isFlippedX()) {
          cx=1.0f;
          sx=-1.0f;
        }
        if (tex.isFlippedY()) {
          cy=1.0f;
          sy=-1.0f;
        }
        renderUa[0]=(cx + sx * a[U]) * uscale;
        renderVa[0]=(cy + sy * a[V]) * vscale;
        renderUb[0]=(cx + sx * b[U]) * uscale;
        renderVb[0]=(cy + sy * b[V]) * vscale;
        renderUc[0]=(cx + sx * c[U]) * uscale;
        renderVc[0]=(cy + sy * c[V]) * vscale;
      }
 else       if (1 < numTextures) {
        for (int t=0; t < numTextures; t++) {
          float uscale=1.0f;
          float vscale=1.0f;
          float cx=0.0f;
          float sx=+1.0f;
          float cy=0.0f;
          float sy=+1.0f;
          PTexture tex=renderTextures[t];
          uscale*=tex.getMaxTexCoordU();
          vscale*=tex.getMaxTexCoordV();
          if (tex.isFlippedX()) {
            cx=1.0f;
            sx=-1.0f;
          }
          if (tex.isFlippedY()) {
            cy=1.0f;
            sy=-1.0f;
          }
          renderUa[t]=(cx + sx * vertexU[na][t]) * uscale;
          renderVa[t]=(cy + sy * vertexV[na][t]) * vscale;
          renderUb[t]=(cx + sx * vertexU[nb][t]) * uscale;
          renderVb[t]=(cy + sy * vertexV[nb][t]) * vscale;
          renderUc[t]=(cx + sx * vertexU[nc][t]) * uscale;
          renderVc[t]=(cy + sy * vertexV[nc][t]) * vscale;
        }
      }
      if (recordingShape) {
        recordedVertices.add(new PVector(a[X],a[Y],a[Z]));
        recordedColors.add(new float[]{a[R],a[G],a[B],a[A]});
        recordedNormals.add(new PVector(a[NX],a[NY],a[NZ]));
        for (int t=0; t < numTextures; t++) {
          recordedTexCoords[t].add(new PVector(renderUa[t],renderVa[t],0.0f));
        }
        for (int t=numTextures; t < maxTextureUnits; t++) {
          recordedTexCoords[t].add(new PVector(0.0f,0.0f,0.0f));
        }
      }
 else {
        vertexArray[3 * n + 0]=toFixed32(a[X]);
        vertexArray[3 * n + 1]=toFixed32(a[Y]);
        vertexArray[3 * n + 2]=toFixed32(a[Z]);
        colorArray[4 * n + 0]=toFixed32(a[R]);
        colorArray[4 * n + 1]=toFixed32(a[G]);
        colorArray[4 * n + 2]=toFixed32(a[B]);
        colorArray[4 * n + 3]=toFixed32(a[A]);
        normalArray[3 * n + 0]=toFixed32(a[NX]);
        normalArray[3 * n + 1]=toFixed32(a[NY]);
        normalArray[3 * n + 2]=toFixed32(a[NZ]);
        for (int t=0; t < numTextures; t++) {
          texCoordArray[t][2 * n + 0]=toFixed32(renderUa[t]);
          texCoordArray[t][2 * n + 1]=toFixed32(renderVa[t]);
        }
        n++;
      }
      if (recordingShape) {
        recordedVertices.add(new PVector(b[X],b[Y],b[Z]));
        recordedColors.add(new float[]{b[R],b[G],b[B],b[A]});
        recordedNormals.add(new PVector(b[NX],b[NY],b[NZ]));
        for (int t=0; t < numTextures; t++) {
          recordedTexCoords[t].add(new PVector(renderUb[t],renderVb[t],0.0f));
        }
        for (int t=numTextures; t < maxTextureUnits; t++) {
          recordedTexCoords[t].add(new PVector(0.0f,0.0f,0.0f));
        }
      }
 else {
        vertexArray[3 * n + 0]=toFixed32(b[X]);
        vertexArray[3 * n + 1]=toFixed32(b[Y]);
        vertexArray[3 * n + 2]=toFixed32(b[Z]);
        colorArray[4 * n + 0]=toFixed32(b[R]);
        colorArray[4 * n + 1]=toFixed32(b[G]);
        colorArray[4 * n + 2]=toFixed32(b[B]);
        colorArray[4 * n + 3]=toFixed32(b[A]);
        normalArray[3 * n + 0]=toFixed32(b[NX]);
        normalArray[3 * n + 1]=toFixed32(b[NY]);
        normalArray[3 * n + 2]=toFixed32(b[NZ]);
        for (int t=0; t < numTextures; t++) {
          texCoordArray[t][2 * n + 0]=toFixed32(renderUb[t]);
          texCoordArray[t][2 * n + 1]=toFixed32(renderVb[t]);
        }
        n++;
      }
      if (recordingShape) {
        recordedVertices.add(new PVector(c[X],c[Y],c[Z]));
        recordedColors.add(new float[]{c[R],c[G],c[B],c[A]});
        recordedNormals.add(new PVector(c[NX],c[NY],c[NZ]));
        for (int t=0; t < numTextures; t++) {
          recordedTexCoords[t].add(new PVector(renderUc[t],renderVc[t],0.0f));
        }
        for (int t=numTextures; t < maxTextureUnits; t++) {
          recordedTexCoords[t].add(new PVector(0.0f,0.0f,0.0f));
        }
      }
 else {
        vertexArray[3 * n + 0]=toFixed32(c[X]);
        vertexArray[3 * n + 1]=toFixed32(c[Y]);
        vertexArray[3 * n + 2]=toFixed32(c[Z]);
        colorArray[4 * n + 0]=toFixed32(c[R]);
        colorArray[4 * n + 1]=toFixed32(c[G]);
        colorArray[4 * n + 2]=toFixed32(c[B]);
        colorArray[4 * n + 3]=toFixed32(c[A]);
        normalArray[3 * n + 0]=toFixed32(c[NX]);
        normalArray[3 * n + 1]=toFixed32(c[NY]);
        normalArray[3 * n + 2]=toFixed32(c[NZ]);
        for (int t=0; t < numTextures; t++) {
          texCoordArray[t][2 * n + 0]=toFixed32(renderUc[t]);
          texCoordArray[t][2 * n + 1]=toFixed32(renderVc[t]);
        }
        n++;
      }
      i++;
    }
    if (!recordingShape) {
      vertexBuffer.put(vertexArray);
      colorBuffer.put(colorArray);
      normalBuffer.put(normalArray);
      for (int t=0; t < numTextures; t++) {
        texCoordBuffer[t].put(texCoordArray[t]);
      }
      vertexBuffer.position(0);
      colorBuffer.position(0);
      normalBuffer.position(0);
      for (int t=0; t < numTextures; t++) {
        texCoordBuffer[t].position(0);
      }
      gl.glVertexPointer(3,GL10.GL_FIXED,0,vertexBuffer);
      gl.glColorPointer(4,GL10.GL_FIXED,0,colorBuffer);
      gl.glNormalPointer(GL10.GL_FIXED,0,normalBuffer);
      for (int t=0; t < numTextures; t++) {
        gl.glClientActiveTexture(GL10.GL_TEXTURE0 + t);
        gl.glTexCoordPointer(2,GL10.GL_FIXED,0,texCoordBuffer[t]);
      }
      gl.glDrawArrays(GL10.GL_TRIANGLES,0,3 * faceLength[j]);
    }
    if (0 < numTextures) {
      if (1 < numTextures) {
        clearMultitextureBlend(numTextures);
      }
      for (int t=0; t < numTextures; t++) {
        PTexture tex=renderTextures[t];
        gl.glActiveTexture(GL10.GL_TEXTURE0 + t);
        gl.glBindTexture(tex.getGLTarget(),0);
      }
      for (int t=0; t < numTextures; t++) {
        PTexture tex=renderTextures[t];
        gl.glDisable(tex.getGLTarget());
      }
      gl.glDisableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
    }
  }
  gl.glDisableClientState(GL10.GL_NORMAL_ARRAY);
  gl.glDisableClientState(GL10.GL_COLOR_ARRAY);
  gl.glDisableClientState(GL10.GL_VERTEX_ARRAY);
  report("String_Node_Str");
}