インラインアセンブリでBrainfu*kインタプリタ

フォーラム(掲示板)ルール
フォーラム(掲示板)ルールはこちら  ※コードを貼り付ける場合は [code][/code] で囲って下さい。詳しくはこちら
アバター
みけCAT
記事: 6734
登録日時: 14年前
住所: 千葉県
連絡を取る:

インラインアセンブリでBrainfu*kインタプリタ

#1

投稿記事 by みけCAT » 14年前

Windows Vista SP2、Dev-C++4.9.9.2、gcc3.4.2です。
インラインアセンブリでBrainfu*kインタプリタを書こうとしています。
参考:Wikipedia
現状のコードだとコンパイルエラーがでます。
どう直せばいいかわからなくて困っています。
どうすればいいか教えていただければ幸いです。

コードは

コード:

#include <stdio.h>
#include <stdlib.h>

int main(int argc,char* argv[]) {
	FILE* infp;
	char* code;
	unsigned char buffer[30000]={0};
	int bufptr=0;
	long size;
	long runptr=0;
	int nowarn=0;
	/*引数チェック*/
	if(argc!=2) {
		fprintf(stderr,"usage:brainfu_k <program source file>\n");
		return 1;
	}
	/*ファイル読み込み*/
	infp=fopen(argv[1],"r");
	if(infp==NULL) {
		fprintf(stderr,"Can't open input file!\n");
		return 2;
	}
	/*サイズの取得*/
	if(fseek(infp,0,SEEK_END)) {
		fclose(infp);
		fprintf(stderr,"File seek error 1.\n");
		return 3;
	}
	size=ftell(infp);
	if(fseek(infp,0,SEEK_SET)) {
		fclose(infp);
		fprintf(stderr,"File seek error 2.\n");
		return 4;
	}
	/*メモリの確保*/
	code=malloc(size);
	if(code==NULL) {
		fclose(infp);
		fprintf(stderr,"Malloc error.\n");
		return 5;
	}
	/*ファイルの読み込み*/
	if(fread(code,1,size,infp)==0) {
		if(ferror(infp)) {
			free(code);
			fclose(infp);
			fprintf(stderr,"File read error.\n");
			return 6;
		}
	}
	/*ファイルクローズ*/
	fclose(infp);
	/*インタプリタ本体*/
	asm volatile(
		"mov $-1,%%ecx\n\t"/*実行ポインタ*/ 
		"mov $0,%%edx\n\t"/*メモリポインタ*/
		"mov %0,%%esi\n\t"/*コード*/
		"mov %1,%%edi\n\t"/*バッファ*/
		"loopstart:\n\t"
		"inc %%ecx\n\t"
		"cmp %2,%%ecx\n\t"/*範囲をオーバーしていたら終了*/
		"jae exitrun\n\t"
		"cmpb $0x3E,(%%esi,%%ecx,1)\n\t"/* > */
		"je pinc\n\t"
		"cmpb $0x3C,(%%esi,%%ecx,1)\n\t"/* < */
		"je pdec\n\t"
		"cmpb $0x2B,(%%esi,%%ecx,1)\n\t"/* + */
		"je minc\n\t"
		"cmpb $0x2D,(%%esi,%%ecx,1)\n\t"/* - */
		"je mdec\n\t"
		"cmpb $0x2E,(%%esi,%%ecx,1)\n\t"/* . */
		"je output\n\t"
		"cmpb $0x2C,(%%esi,%%ecx,1)\n\t"/* , */
		"je input\n\t"
		"cmpb $0x5B,(%%esi,%%ecx,1)\n\t"/* [ */
		"je startploop\n\t"
		"cmpb $0x5D,(%%esi,%%ecx,1)\n\t"/* ] */
		"je endploop\n\t"
		"jmp loopstart\n\t"/*該当なし*/
		"pinc:\n\t"/* > */
		"inc %%edx\n\t"
		"cmp $0,%%edx\n\t"/*範囲チェック*/
		"jb exitrun\n\t"
		"cmp $30000,%%edx\n\t"
		"jae exitrun\n\t"
		"jmp loopstart\n\t"
		"pdec:\n\t"/* < */
		"dec %%edx\n\t"
		"cmp $0,%%edx\n\t"/*範囲チェック*/
		"jb exitrun\n\t"
		"cmp $30000,%%edx\n\t"
		"jae exitrun\n\t"
		"jmp loopstart\n\t"
		"minc:\n\t"/* + */
		"incb (%%edi,%%edx,1)\n\t"
		"jmp loopstart\n\t"
		"mdec:\n\t"/* - */
		"decb (%%edi,%%edx,1)\n\t"
		"jmp loopstart\n\t"
		"output:\n\t"/* . */
		"mov $0,%%ebx\n\t"
		"mov (%%edi,%%edx,1),%%bl\n\t"
		"push %%ebx\n\t"
		"call putchar\n\t"
		"jmp loopstart\n\t"
		"input:\n\t"/* , */
		"call getchar\n\t"
		"mov %%eax,(%%edi,%%edx,1)\n\t"
		"jmp loopstart\n\t"
		"startploop:\n\t"/* [ */
		"mov $1,%%eax\n\t"
		"searchend:\n\t"
		"inc %%ecx\n\t"
		"cmp %2,%%ecx\n\t"/*範囲をオーバーしていたら終了*/
		"jae exitrun\n\t"
		"cmpb $0x5B,(%%esi,%%ecx,1)\n\t"/* [ */
		"je plus\n\t"
		"cmpb $0x5D,(%%esi,%%ecx,1)\n\t"/* ] */
		"je minus\n\t"
		"jmp searchend\n\t"
		"plus:\n\t"
		"inc %%eax\n\t"
		"jmp searchend\n\t"
		"minus:\n\t"
		"dec %%eax\n\t"
		"cmp $0,%%eax\n\t"
		"jbe loopstart\n\t"
		"jmp searchend\n\t"
		"endploop:\n\t"/* ] */
		"mov $1,%%eax\n\t"
		"searchend2:\n\t"
		"dec %%ecx\n\t"
		"cmp $0,%%ecx\n\t"/*範囲をオーバーしていたら終了*/
		"jb exitrun\n\t"
		"cmpb $0x5B,(%%esi,%%ecx,1)\n\t"/* [ */
		"je minus2\n\t"
		"cmpb $0x5D,(%%esi,%%ecx,1)\n\t"/* ] */
		"je plus2\n\t"
		"jmp searchend2\n\t"
		"plus2:\n\t"
		"inc %%eax\n\t"
		"jmp searchend2\n\t"
		"minus2:\n\t"
		"dec %%eax\n\t"
		"cmp $0,%%eax\n\t"
		"jbe loopstart\n\t"
		"jmp searchend2\n\t"
		"exitrun:\n\t"/*終了*/
	:
	: "m"(code),"m"(buffer),"m"(size)
	: "%eax","%ebx","%ecx","%edx","%esi","%edi");
	/*メモリの開放*/
	free(code);
	return 0;
}
エラーは

H:\C\bfiasm\bfiasm.c: In function `main':
H:\C\bfiasm\bfiasm.c:54: warning: use of memory input without lvalue in asm operand 1 is deprecated
C:\Users\****\AppData\Local\Temp/cceWdaaa.o(.text+0x30a):bfiasm.c: undefined reference to `putchar'
C:\Users\****\AppData\Local\Temp/cceWdaaa.o(.text+0x314):bfiasm.c: undefined reference to `getchar'
collect2: ld returned 1 exit status

です。(****はユーザー名)
よろしくお願いします。
複雑な問題?マシンの性能を上げてOpenMPで殴ればいい!(死亡フラグ)

“C言語何でも質問掲示板” へ戻る