mkgra.c
来自「DGen源码最后版本」· C语言 代码 · 共 270 行
C
270 行
#include <stdio.h>#include <stdlib.h>#include <string.h>// Builder for the gra.asm NASM module// Renders md tiles// Currently 15-bit and 16-bit are the same, since// the palette value is just copied across, so use draw_tile_16() for bothstatic int depth_to_bytes(int depth){ if (depth<=8) return 1; else if (depth<=16) return 2; else if (depth<=24) return 3; else return 4;}static int emit_clear_to_col(FILE *hand,int bpp){ fprintf (hand,";extern \"C\" int clear_to_col_%d\n",bpp); fprintf (hand, "; (unsigned char *dest,int len,unsigned int col);\n" "\n" ); fprintf (hand,"global _clear_to_col_%d\n",bpp); fprintf (hand,"times ($$-$) & 3 db 0\n"); fprintf (hand,"_clear_to_col_%d:\n",bpp); fprintf (hand, "push edi\n" "push ecx\n" "mov edi,[esp+12] ; edi is a pointer to the bitmap\n" "mov ecx,[esp+16] ; ecx is the amount of pixel to clear\n" "mov eax,[esp+20] ; eax is the color\n" ); if (bpp<=8) fprintf (hand,"rep stosb\n"); else if (bpp<=16) fprintf (hand,"rep stosw\n"); else if (bpp<=24) { fprintf (hand,"clear_to_col_twenty_four:\n"); fprintf (hand," stosw\n"); fprintf (hand," ror eax,16\n"); fprintf (hand," stosb\n"); fprintf (hand," rol eax,16\n"); fprintf (hand,"loop clear_to_col_twenty_four\n"); ; // help! } else fprintf (hand,"rep stosd\n"); fprintf (hand, "pop ecx\n" "pop edi\n" "xor eax,eax\n" "ret\n" "\n\n\n" ); return 0;}static int emit_draw_tile(FILE *hand,int bpp,int flip,int interlace){ static int label_no=0;// static int xloop_no=0,yloop_no=0; // flip&1 = horizontal flip flip&2 = vertical flip static char fname[4][7]={"","_hf","_vf","_hf_vf"}; flip&=3; fprintf (hand, "; (unsigned char *dest,int pitch,unsigned char *tilep,unsigned int *palette);\n" ";// %%1 %%2 %%3 %%4\n" "\n" ); fprintf (hand,"global _draw_tile_%s%d%s\n",interlace?"i_":"",bpp,fname[flip]); fprintf (hand,"times ($$-$) & 3 db 0\n"); fprintf (hand,"_draw_tile_%s%d%s:\n",interlace?"i_":"",bpp,fname[flip]); fprintf (hand, "\n" "push ebx\n" "push ecx\n" "push edx\n" "push esi\n" "push edi\n" "push ebp\n" "\n" "mov edi,[esp+28] ; edi is a pointer to the screen\n" "mov ebx,[esp+32]\n" "mov esi,[esp+36] ; esi is a pointer to the tilep\n" "mov ebp,[esp+40] ; ebp is a pointer to the palette\n" ); if (flip&2) { fprintf (hand,"mov eax,ebx\n"); fprintf (hand,"sal eax,3\n"); fprintf (hand,"sub eax,ebx ; eax=pitch*7\n"); fprintf (hand,"add edi,eax ; point to bottom line of tile dest\n"); fprintf (hand,"neg ebx\n"); } if (flip&1) { fprintf (hand,"add ebx,%d\n",8*depth_to_bytes(bpp)); fprintf (hand,"add edi,%d\n",7*depth_to_bytes(bpp)); } else fprintf (hand,"sub ebx,%d\n",8*depth_to_bytes(bpp)); { int x,y;// fprintf (hand,"and cl,0x0f; Loop 8 times (till cl&0x80==0x80)\n");// fprintf (hand,"yloop_%d:\n",yloop_no); for (y=0;y<8;y++) // Unroll above loop {// fprintf (hand,"and cl,0xf0; Loop 4 times (till cl&0x04==0x04)\n");// fprintf (hand,"xloop_%d:\n",xloop_no); for (x=0;x<8;x++) // x<8 means Unroll above loop { // dl is tilep byte // eax is the colour we are going to draw // high bits of edx and ecx are currently unused if ((x&1)==0) fprintf (hand,"mov dl,byte[esi]; Get tile pixel\n"); else fprintf (hand,"rol dl,4 ; Get tile pixel\n"); fprintf (hand,"mov al,dl\n"); fprintf (hand,"and eax,0xf0 ; palette index now in bits 4-7 of eax\n"); fprintf (hand,"test eax,0xf0\n"); fprintf (hand,"jz trans_%.4x\n",label_no); fprintf (hand,"ror al,4\n"); fprintf (hand,"mov eax,[ebp+eax*4] ; look up colour in palette\n"); //fprintf (hand,"mov eax,0x%.8x\n", ((x<<2)<<11) | (y<<2) ); if (bpp==8) fprintf (hand,"mov byte[edi],al\n"); else if (bpp==15 || bpp==16) fprintf (hand,"mov word[edi],ax\n"); else if (bpp==24) { fprintf (hand,"mov byte[edi],al\ninc edi\nror eax,8\n"); fprintf (hand,"mov byte[edi],al\ninc edi\nror eax,8\n"); fprintf (hand,"mov byte[edi],al\nsub edi,2\n"); } else if (bpp==32) fprintf (hand,"mov dword[edi],eax\n"); fprintf (hand,"trans_%.4x:\n",label_no); if ((x&1)==1) fprintf (hand,"inc esi\n"); fprintf (hand,"%s edi,%d\n",(flip&1)?"sub":"add",depth_to_bytes(bpp)); label_no++; } if (interlace) fprintf (hand,"add esi,4 ; interlace mode\n");// fprintf (hand,"inc cl\n");// fprintf (hand,"test cl,0x04 ; Looped 4 times yet?\n");// fprintf (hand,"jz xloop_%d\n",xloop_no); xloop_no++; fprintf (hand,"add edi,ebx\n"); }// fprintf (hand,"add cl,0x10\n");// fprintf (hand,"test cl,0x80 ; Looped 8 times yet?\n");// fprintf (hand,"jz yloop_%d\n",yloop_no);// yloop_no++; } fprintf (hand, "pop ebp\n" "pop edi\n" "pop esi\n" "pop edx\n" "pop ecx\n" "pop ebx\n" "xor eax,eax\n" "\n" "ret\n" "\n\n\n" ); return 0;}int main(){ FILE *hand=NULL; static char outname[]="gra.asm"; hand=fopen(outname,"wt"); if (hand==NULL) { printf ("Couldn't open %s\n",outname); return 1; } fprintf (hand, "; Note - this file is automatically generated by mkgra.c\n\n" "bits 32\n" "section .text\n"/* "global _dave_var\n" "_dave_var:\n" "dd 123\n" ";__memoryreadbyte dd 0\n" ";__dreg dd 0,0,0,0,0,0,0,0\n" "section .text\n" "bits 32\n" "top:\n" "\n" "global _daves_asm\n" "times ($$-$) & 3 db 0\n" "_daves_asm:\n" "\n" "push ebx\n" "push ecx\n" "push edx\n" "push esi\n" "push edi\n" "\n" "mov eax,[esp+24]\n" "mov ebx,dword[_dave_var]\n" "add eax,ebx\n" "\n" "pop edi\n" "pop esi\n" "pop edx\n" "pop ecx\n" "pop ebx\n" "\n" "ret\n" "\n"*/ ); { static int dep[4]={8,16,24,32}; int d,f,i; for (d=0;d<4;d++) { emit_clear_to_col(hand,dep[d]); for (i=0;i<2;i++) for (f=0;f<4;f++) { emit_draw_tile(hand,dep[d],f,i); } } } fclose(hand); return 0;}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?