static inline void dumpArbProgram(StateWriter &writer, Context &context, GLenum target) { if (context.ES || context.core || !glIsEnabled(target)) { return; } GLint program_length = 0; glGetProgramivARB(target, GL_PROGRAM_LENGTH_ARB, &program_length); if (!program_length) { return; } GLchar *source = new GLchar[program_length + 1]; source[0] = 0; glGetProgramStringARB(target, GL_PROGRAM_STRING_ARB, source); source[program_length] = 0; writer.beginMember(enumToString(target)); writer.writeString(source); writer.endMember(); delete [] source; }
static inline void dumpArbProgram(JSONWriter &json, GLenum target) { if (!glIsEnabled(target)) { return; } GLint program_length = 0; glGetProgramivARB(target, GL_PROGRAM_LENGTH_ARB, &program_length); if (!program_length) { return; } GLchar *source = new GLchar[program_length + 1]; source[0] = 0; glGetProgramStringARB(target, GL_PROGRAM_STRING_ARB, source); source[program_length] = 0; json.beginMember(enumToString(target)); json.writeString(source); json.endMember(); delete [] source; }
JNIEXPORT void JNICALL Java_org_lwjgl_opengl_ARBProgram_nglGetProgramStringARB(JNIEnv *env, jclass clazz, jint target, jint parameterName, jlong paramString, jlong function_pointer) { GLvoid *paramString_address = (GLvoid *)(intptr_t)paramString; glGetProgramStringARBPROC glGetProgramStringARB = (glGetProgramStringARBPROC)((intptr_t)function_pointer); glGetProgramStringARB(target, parameterName, paramString_address); }
JNIEXPORT void JNICALL Java_org_lwjgl_opengl_ARBVertexProgram_nglGetProgramStringARB(JNIEnv *__env, jclass clazz, jint target, jint pname, jlong stringAddress) { glGetProgramStringARBPROC glGetProgramStringARB = (glGetProgramStringARBPROC)tlsGetFunction(1393); intptr_t string = (intptr_t)stringAddress; UNUSED_PARAM(clazz) glGetProgramStringARB(target, pname, string); }
JNIEXPORT void JNICALL Java_org_lwjgl_opengl_ARBProgram_nglGetProgramStringARB(JNIEnv *env, jclass clazz, jint target, jint parameterName, jobject paramString, jint paramString_position, jlong function_pointer) { GLvoid *paramString_address = ((GLvoid *)(((char *)(*env)->GetDirectBufferAddress(env, paramString)) + paramString_position)); glGetProgramStringARBPROC glGetProgramStringARB = (glGetProgramStringARBPROC)((intptr_t)function_pointer); glGetProgramStringARB(target, parameterName, paramString_address); }
/* * Interactive debugger */ static void Debugger2(GLenum target, GLvoid *data) { static GLuint skipCount = 0; const GLubyte *ln; GLint pos, line, column; GLint id; int progType; GLint len; GLubyte *program; GLboolean stop; int i; /* Sigh, GL_VERTEX_PROGRAM_ARB == GL_VERTEX_PROGRAM_NV so it's a bit * hard to distinguish between them. */ if (target == GL_FRAGMENT_PROGRAM_ARB) progType = ARB_FRAGMENT_PROGRAM; else if (target == GL_FRAGMENT_PROGRAM_NV) progType = NV_FRAGMENT_PROGRAM; else progType = NV_VERTEX_PROGRAM; /* Until we hit zero, continue rendering */ if (skipCount > 0) { skipCount--; return; } /* Get id of the program and current position */ switch (progType) { case ARB_FRAGMENT_PROGRAM: glGetProgramivARB(GL_FRAGMENT_PROGRAM_ARB, GL_PROGRAM_BINDING_ARB, &id); glGetIntegerv(GL_FRAGMENT_PROGRAM_POSITION_MESA, &pos); break; case NV_FRAGMENT_PROGRAM: glGetIntegerv(GL_FRAGMENT_PROGRAM_BINDING_NV, &id); glGetIntegerv(GL_FRAGMENT_PROGRAM_POSITION_MESA, &pos); break; case ARB_VERTEX_PROGRAM: glGetProgramivARB(GL_VERTEX_PROGRAM_ARB, GL_PROGRAM_BINDING_ARB, &id); glGetIntegerv(GL_VERTEX_PROGRAM_POSITION_MESA, &pos); break; case NV_VERTEX_PROGRAM: glGetIntegerv(GL_VERTEX_PROGRAM_BINDING_NV, &id); glGetIntegerv(GL_VERTEX_PROGRAM_POSITION_MESA, &pos); break; default: abort(); } /* get program string */ if (progType == ARB_VERTEX_PROGRAM || progType == ARB_FRAGMENT_PROGRAM) glGetProgramivARB(target, GL_PROGRAM_LENGTH_ARB, &len); else glGetProgramivNV(id, GL_PROGRAM_LENGTH_NV, &len); program = malloc(len + 1); if (progType == ARB_VERTEX_PROGRAM || progType == ARB_FRAGMENT_PROGRAM) glGetProgramStringARB(target, GL_PROGRAM_STRING_ARB, program); else glGetProgramStringNV(id, GL_PROGRAM_STRING_NV, program); /* Get current line number, column, line string */ ln = find_line_column(program, program + pos, &line, &column); /* test breakpoints */ if (NumBreakpoints > 0) stop = GL_FALSE; else stop = GL_TRUE; for (i = 0; i < NumBreakpoints; i++) { if (Breakpoints[i].enabled) { switch (Breakpoints[i].type) { case PIXEL: if (progType == ARB_FRAGMENT_PROGRAM) { } else if (progType == NV_FRAGMENT_PROGRAM) { GLfloat pos[4]; int px, py; glGetProgramRegisterfvMESA(GL_FRAGMENT_PROGRAM_NV, 6, (GLubyte *) "f[WPOS]", pos); px = (int) pos[0]; py = (int) pos[1]; printf("%d, %d\n", px, py); if (px == Breakpoints[i].x && py == Breakpoints[i].y) { printf("Break at pixel (%d, %d)\n", px, py); stop = GL_TRUE; } } break; case LINE: if (line == Breakpoints[i].line) { /* hit a breakpoint! */ printf("Break at line %d\n", line); stop = GL_TRUE; } break; } } } if (!stop) { free(program); return; } printf("%d: %s\n", line, ln); /* get commands from stdin */ while (1) { char command[1000], *cmd; /* print prompt and get command */ printf("(%s %d) ", (target == GL_VERTEX_PROGRAM_ARB ? "vert" : "frag"), line); fgets(command, 999, stdin); /* skip leading whitespace */ for (cmd = command; cmd[0] == ' '; cmd++) ; if (!cmd[0]) /* nothing (repeat the previous cmd?) */ continue; switch (cmd[0]) { case 's': /* skip N instructions */ i = atoi(cmd + 2); skipCount = i; printf("Skipping %d instructions\n", i); return; case 'n': /* next */ return; case 'c': return; case 'd': /* dump machine state */ if (progType == NV_FRAGMENT_PROGRAM) { static const char *inRegs[] = { "f[WPOS]", "f[COL0]", "f[COL1]", "f[FOGC]", "f[TEX0]", "f[TEX1]", "f[TEX2]", "f[TEX3]", NULL }; static const char *outRegs[] = { "o[COLR]", "o[COLH]", "o[DEPR]", NULL }; GLfloat v[4]; int i; printf("Fragment input attributes:\n"); for (i = 0; inRegs[i]; i++) { glGetProgramRegisterfvMESA(GL_FRAGMENT_PROGRAM_NV, strlen(inRegs[i]), (const GLubyte *) inRegs[i], v); printf(" %s: %g, %g, %g, %g\n", inRegs[i], v[0], v[1], v[2], v[3]); } printf("Fragment output attributes:\n"); for (i = 0; outRegs[i]; i++) { glGetProgramRegisterfvMESA(GL_FRAGMENT_PROGRAM_NV, strlen(outRegs[i]), (const GLubyte *) outRegs[i], v); printf(" %s: %g, %g, %g, %g\n", outRegs[i], v[0], v[1], v[2], v[3]); } printf("Temporaries:\n"); for (i = 0; i < 4; i++) { char temp[100]; GLfloat v[4]; sprintf(temp, "R%d", i); glGetProgramRegisterfvMESA(GL_FRAGMENT_PROGRAM_NV, strlen(temp), (const GLubyte *) temp, v); printf(" %s: %g, %g, %g, %g\n", temp, v[0],v[1],v[2],v[3]); } } else if (progType == NV_VERTEX_PROGRAM) { GLfloat v[4]; int i; static const char *inRegs[] = { "v[OPOS]", "v[WGHT]", "v[NRML]", "v[COL0]", "v[COL1]", "v[FOGC]", "v[6]", "v[7]", "v[TEX0]", "v[TEX1]", "v[TEX2]", "v[TEX3]", "v[TEX4]", "v[TEX5]", "v[TEX6]", "v[TEX7]", NULL }; static const char *outRegs[] = { "o[HPOS]", "o[COL0]", "o[COL1]", "o[BFC0]", "o[BFC1]", "o[FOGC]", "o[PSIZ]", "o[TEX0]", "o[TEX1]", "o[TEX2]", "o[TEX3]", "o[TEX4]", "o[TEX5]", "o[TEX6]", "o[TEX7]", NULL }; printf("Vertex input attributes:\n"); for (i = 0; inRegs[i]; i++) { glGetProgramRegisterfvMESA(GL_VERTEX_PROGRAM_NV, strlen(inRegs[i]), (const GLubyte *) inRegs[i], v); printf(" %s: %g, %g, %g, %g\n", inRegs[i], v[0], v[1], v[2], v[3]); } printf("Vertex output attributes:\n"); for (i = 0; outRegs[i]; i++) { glGetProgramRegisterfvMESA(GL_VERTEX_PROGRAM_NV, strlen(outRegs[i]), (const GLubyte *) outRegs[i], v); printf(" %s: %g, %g, %g, %g\n", outRegs[i], v[0], v[1], v[2], v[3]); } printf("Temporaries:\n"); for (i = 0; i < 4; i++) { char temp[100]; GLfloat v[4]; sprintf(temp, "R%d", i); glGetProgramRegisterfvMESA(GL_VERTEX_PROGRAM_NV, strlen(temp), (const GLubyte *) temp, v); printf(" %s: %g, %g, %g, %g\n", temp, v[0],v[1],v[2],v[3]); } } break; case 'l': /* list */ list_program(program, len); break; case 'p': /* print */ { GLfloat v[4]; char *c; cmd++; while (*cmd == ' ') cmd++; c = cmd; while (*c) { if (*c == '\n' || *c == '\r') *c = 0; else c++; } glGetProgramRegisterfvMESA(target, strlen(cmd), (const GLubyte *) cmd, v); if (glGetError() == GL_NO_ERROR) printf("%s = %g, %g, %g, %g\n", cmd, v[0], v[1], v[2], v[3]); else printf("Invalid expression\n"); } break; case 'b': if (cmd[1] == ' ' && isdigit(cmd[2])) { char *comma = strchr(cmd, ','); if (comma) { /* break at pixel */ int x = atoi(cmd + 2); int y = atoi(comma + 1); if (NumBreakpoints < MAX_BREAKPOINTS) { Breakpoints[NumBreakpoints].type = PIXEL; Breakpoints[NumBreakpoints].x = x; Breakpoints[NumBreakpoints].y = y; Breakpoints[NumBreakpoints].enabled = GL_TRUE; NumBreakpoints++; printf("Breakpoint %d: break at pixel (%d, %d)\n", NumBreakpoints, x, y); } } else { /* break at line */ int l = atoi(cmd + 2); if (l && NumBreakpoints < MAX_BREAKPOINTS) { Breakpoints[NumBreakpoints].type = LINE; Breakpoints[NumBreakpoints].line = l; Breakpoints[NumBreakpoints].enabled = GL_TRUE; NumBreakpoints++; printf("Breakpoint %d: break at line %d\n", NumBreakpoints, l); } } } else { /* list breakpoints */ printf("Breakpoints:\n"); for (i = 0; i < NumBreakpoints; i++) { switch (Breakpoints[i].type) { case LINE: printf(" %d: break at line %d\n", i + 1, Breakpoints[i].line); break; case PIXEL: printf(" %d: break at pixel (%d, %d)\n", i + 1, Breakpoints[i].x, Breakpoints[i].y); break; } } } break; case 'h': /* help */ printf("Debugger commands:\n"); printf(" b list breakpoints\n"); printf(" b N break at line N\n"); printf(" b x,y break at pixel x,y\n"); printf(" c continue execution\n"); printf(" d display register values\n"); printf(" h help\n"); printf(" l list program\n"); printf(" n next instruction\n"); printf(" p V print value V\n"); printf(" s N skip N instructions\n"); break; default: printf("Unknown command: %c\n", cmd[0]); } } }