0,0 → 1,251 |
#include "zgl.h" |
|
static char *op_table_str[]= |
{ |
#define ADD_OP(a,b,c) "gl" #a " " #c, |
|
#include "opinfo.h" |
}; |
|
static void (*op_table_func[])(GLContext *,GLParam *)= |
{ |
#define ADD_OP(a,b,c) glop ## a , |
|
#include "opinfo.h" |
}; |
|
static int op_table_size[]= |
{ |
#define ADD_OP(a,b,c) b + 1 , |
|
#include "opinfo.h" |
}; |
|
|
|
static GLList *find_list(GLContext *c,unsigned int list) |
{ |
return c->shared_state.lists[list]; |
} |
|
static void delete_list(GLContext *c,int list) |
{ |
GLParamBuffer *pb,*pb1; |
GLList *l; |
|
l=find_list(c,list); |
assert(l != NULL); |
|
/* free param buffer */ |
pb=l->first_op_buffer; |
while (pb!=NULL) { |
pb1=pb->next; |
gl_free(pb); |
pb=pb1; |
} |
|
gl_free(l); |
c->shared_state.lists[list]=NULL; |
} |
|
static GLList *alloc_list(GLContext *c,int list) |
{ |
GLList *l; |
GLParamBuffer *ob; |
|
l=gl_zalloc(sizeof(GLList)); |
ob=gl_zalloc(sizeof(GLParamBuffer)); |
|
ob->next=NULL; |
l->first_op_buffer=ob; |
|
ob->ops[0].op=OP_EndList; |
|
c->shared_state.lists[list]=l; |
return l; |
} |
|
|
void gl_print_op(FILE *f,GLParam *p) |
{ |
int op; |
char *s; |
|
op=p[0].op; |
p++; |
s=op_table_str[op]; |
while (*s != 0) { |
if (*s == '%') { |
s++; |
switch (*s++) { |
case 'f': |
fprintf(f,"%g",p[0].f); |
break; |
default: |
fprintf(f,"%d",p[0].i); |
break; |
} |
p++; |
} else { |
fputc(*s,f); |
s++; |
} |
} |
fprintf(f,"\n"); |
} |
|
|
void gl_compile_op(GLContext *c,GLParam *p) |
{ |
int op,op_size; |
GLParamBuffer *ob,*ob1; |
int index,i; |
|
op=p[0].op; |
op_size=op_table_size[op]; |
index=c->current_op_buffer_index; |
ob=c->current_op_buffer; |
|
/* we should be able to add a NextBuffer opcode */ |
if ((index + op_size) > (OP_BUFFER_MAX_SIZE-2)) { |
|
ob1=gl_zalloc(sizeof(GLParamBuffer)); |
ob1->next=NULL; |
|
ob->next=ob1; |
ob->ops[index].op=OP_NextBuffer; |
ob->ops[index+1].p=(void *)ob1; |
|
c->current_op_buffer=ob1; |
ob=ob1; |
index=0; |
} |
|
for(i=0;i<op_size;i++) { |
ob->ops[index]=p[i]; |
index++; |
} |
c->current_op_buffer_index=index; |
} |
|
void gl_add_op(GLParam *p) |
{ |
GLContext *c=gl_get_context(); |
int op; |
|
op=p[0].op; |
if (c->exec_flag) { |
op_table_func[op](c,p); |
} |
if (c->compile_flag) { |
gl_compile_op(c,p); |
} |
if (c->print_flag) { |
gl_print_op(stderr,p); |
} |
} |
|
/* this opcode is never called directly */ |
void glopEndList(GLContext *c,GLParam *p) |
{ |
assert(0); |
} |
|
/* this opcode is never called directly */ |
void glopNextBuffer(GLContext *c,GLParam *p) |
{ |
assert(0); |
} |
|
|
void glopCallList(GLContext *c,GLParam *p) |
{ |
GLList *l; |
int list,op; |
|
list=p[1].ui; |
l=find_list(c,list); |
if (l == NULL) gl_fatal_error("list %d not defined",list); |
p=l->first_op_buffer->ops; |
|
while (1) { |
op=p[0].op; |
if (op == OP_EndList) break; |
if (op == OP_NextBuffer) { |
p=(GLParam *)p[1].p; |
} else { |
op_table_func[op](c,p); |
p+=op_table_size[op]; |
} |
} |
} |
|
|
|
void glNewList(unsigned int list,int mode) |
{ |
GLList *l; |
GLContext *c=gl_get_context(); |
|
assert(mode == GL_COMPILE || mode == GL_COMPILE_AND_EXECUTE); |
assert(c->compile_flag == 0); |
|
l=find_list(c,list); |
if (l!=NULL) delete_list(c,list); |
l=alloc_list(c,list); |
|
c->current_op_buffer=l->first_op_buffer; |
c->current_op_buffer_index=0; |
|
c->compile_flag=1; |
c->exec_flag=(mode == GL_COMPILE_AND_EXECUTE); |
} |
|
void glEndList(void) |
{ |
GLContext *c=gl_get_context(); |
GLParam p[1]; |
|
assert(c->compile_flag == 1); |
|
/* end of list */ |
p[0].op=OP_EndList; |
gl_compile_op(c,p); |
|
c->compile_flag=0; |
c->exec_flag=1; |
} |
|
int glIsList(unsigned int list) |
{ |
GLContext *c=gl_get_context(); |
GLList *l; |
l=find_list(c,list); |
return (l != NULL); |
} |
|
unsigned int glGenLists(int range) |
{ |
GLContext *c=gl_get_context(); |
int count,i,list; |
GLList **lists; |
|
lists=c->shared_state.lists; |
count=0; |
for(i=0;i<MAX_DISPLAY_LISTS;i++) { |
if (lists[i]==NULL) { |
count++; |
if (count == range) { |
list=i-range+1; |
for(i=0;i<range;i++) { |
alloc_list(c,list+i); |
} |
return list; |
} |
} else { |
count=0; |
} |
} |
return 0; |
} |
|