0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

Brainfuck compiler to x86_64 on linux by C and python

Last updated at Posted at 2024-12-10

Brainfuckのコンパイラです。C版とPython版があります。x86_64のアセンブリコードに落とします。

C

bfs.c
#include    <stdio.h>
#include    <stdlib.h>
static int loopstack[1000];
static int lsp=0;

void lsout() {
    for (int i=0;i<lsp;i++)
        printf("%d_",loopstack[i]);
}

void main(int argc,char *argv[]) {
    FILE *fp;
    int  c,lf;
    if (argc!=2) {
        fprintf(stderr,"Usage: bfs <file>\n");
        exit(1);
    }
    fp=fopen(argv[1],"rt");
    if (fp==NULL) {
        fprintf(stderr,"File open error.\n");
        exit(1);
    }

	printf("\t.section .text\n");
	printf("\t.globl _start\n");
    printf("_start:\n");
    printf("\tmovabs $_my_data,%%rsi\n");
    printf("\tmov\t$1,%%edx\n");

    lsp=0;
    lf='[';
    while((c=fgetc(fp))!=EOF) {
        switch (c) {
            case '>':
                printf("\tinc\t%%rsi\n");
                break;
            case '<':
                printf("\tdec\t%%rsi\n");
                break;
            case '+':
				printf("\tincb\t(%%rsi)\n");
                break;
            case '-':
				printf("\tdecb\t(%%rsi)\n");
                break;
            case '.':
				printf("\tmov\t%%edx,%%eax\n");
				printf("\tmov\t%%edx,%%ebx\n");
				printf("\tsyscall\n");
                break;
            case ',':
				printf("\txor\t%%eax, %%eax\n");
				printf("\txor\t%%ebx, %%ebx\n");
				printf("\tsyscall\n");
                break;
            case '[':
                if (lf==']')
                    loopstack[(lsp-1)]++;
                else
                    loopstack[lsp++]=1;
                lf='[';
                printf("\tjmp LE"); lsout(); printf("\n");
                printf("LB"); lsout(); printf(":\n");
                break;
            case ']':
                if (lf==']')
                    lsp--;
                lf=']';
                printf("LE"); lsout(); printf(":\n");
	            printf("\tcmp\t%%dh,(%%rsi)\n");
                printf("\tjne\tLB"); lsout(); printf("\n");
                break;
            default:
            }
    }
    fclose(fp);
    printf("\tmov\t$1,%%eax\n");
    printf("\txor\t%%ebx,%%ebx\n");
    printf("\tint $0x80\n");
    printf(".section .bss\n");
    printf("_my_data: .zero 65536\n");
    exit(0);
}

コンパイル:cc bfs.c -o bfs
brainfuckコードのコンパイル:./bfs file.bf >file.s
アセンブル:as file.s -o file.o
リンク:ld file.o -o file.exe
実行:./file.exe

Python版

bfs.py
#!/usr/bin/python3
import sys

def lsout(loopstack):
    return str(loopstack).replace(', ','_').replace('[','').replace(']','')

def main():
    if len(sys.argv)!=2:
        print(f"Usage: {sys.argv[0]} <file>")
        return
    print("    .section .text")
    print("    .globl _start")
    print("_start:")
    print("    movabs $_my_data,%rsi")
    print("    mov    $1,%edx")

    f=open(sys.argv[1],"rt")
    loopstack=[]
    lf='['
    for s in f:
        for c in s:
            if c=='>':
                print("    inc     %rsi")
            elif c=='<':
                print("    dec     %rsi")
            elif c=='+':
                print("    incb     (%rsi)")
            elif c=='-':
                print("    decb     (%rsi)")
            elif c=='.':
                print("    mov     %edx,%eax")
                print("    mov     %edx,%ebx")
                print("    syscall")
            elif c==',':
                print("    xor     %eax,%eax")
                print("    xor     %ebx,%ebx")
                print("    syscall")
            elif c=='[':
                if lf==']':
                    loopstack[len(loopstack)-1]+=1
                else:
                    loopstack.append(1)
                lf='['
                print(f"    jmp     LE{lsout(loopstack)}")
                print(f"LB{lsout(loopstack)}:")
            elif c==']':
                if lf==']':
                    loopstack.pop()
                lf=']'
                print(f"LE{lsout(loopstack)}:")
                print("    cmp     %dh,(%rsi)")
                print(f"    jne     LB{lsout(loopstack)}")
    f.close()
    print("    mov     $1,%eax")
    print("    xor     %ebx,%ebx")
    print("    int $0x80")
    print(".section .bss")
    print("_my_data: .zero 65536")

if __name__=='__main__':
    main()
    exit(0)

実行権の付与:chmod +x bfs.py
brainfuckコードのコンパイル:./bfs.py file.bf >file.s
アセンブル:as file.s -o file.o
リンク:ld file.o -o file.exe
実行:./file.exe

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?