最初コミット

This commit is contained in:
2025-11-30 22:03:38 +09:00
commit 7426a775b1
8 changed files with 258 additions and 0 deletions

3
.gitignore vendored Normal file
View File

@@ -0,0 +1,3 @@
*.o
*.core
server

12
Makefile Normal file
View File

@@ -0,0 +1,12 @@
all:
nasm -f elf64 main.s -o main.o
ld main.o -o server
debug:
nasm -f elf64 -g -F dwarf main.s -o main.o
ld main.o -o server
clean:
rm -rf main.o server
.PHONY: all debug clean

2
README.md Normal file
View File

@@ -0,0 +1,2 @@
x64アセンブリ言語で書かれた概念実証のHTTPサーバー\
未完了

53
file.s Normal file
View File

@@ -0,0 +1,53 @@
section .text
load_file:
; ファイルの開く
mov rax, 5 ; sys_open
mov rdi, filename
mov rsi, 0 ; O_RDONLY
mov rdx, 0
mov rax, 499 ; sys_openat
; mov rax, 547
; mov rdi, -100 ; AT_FDCWD
; mov rsi, filename
; mov rdx, 0 ; O_RDONLY
; mov r10, 0 ; モード(見逃し)
syscall
cmp rax, 0
jl .fail
mov [filefd], rax
; ファイルサイズの受け取り
mov rax, 478 ; sys_lseek
mov rdi, [filefd]
xor rsi, rsi
mov rdx, 2 ; SEEK_END
syscall
mov [file_size], rax
; 初めからシーク
mov rax, 478
xor rsi, rsi
mov rdx, 0 ; SEEK_SET
syscall
; ファイルの全部の読み込み
mov rax, 3 ; sys_read
mov rdi, [filefd]
mov rsi, file_buf
mov rdx, [file_size]
syscall
; ファイルを閉じる
mov rax, 6 ; sys_close
mov rdi, [filefd]
syscall
xor rax, rax ; 成功
ret
.fail:
mov rax, -1
ret

139
main.s Normal file
View File

@@ -0,0 +1,139 @@
; このサーバーのコードははFreeBSD向けに書きました。
; Linuxに実行するには、syscall番号を変更して下さい。
section .data
filename db "./www/index.html", 0x0
at_fd dq -0x64
listen_msg db " http://0.0.0.0:8000/ ", 0xa, 0x0
listen_len equ $-listen_msg-1
; 1101
http_header db "HTTP/1.1 200 OK", 0xd, 0xa
db "Content-Type: text/html", 0xd, 0xa
db "Connection: close", 0xd, 0xa
db "Content-Length: "
clen_str db " ", 0xd, 0xa, 0xd, 0xa, 0x0
notfound db "HTTP/1.1 404 Not Found", 0xd, 0xa,
db "Content-Length: 0", 0xd, 0xa, 0xd, 0xa, 0x0
section .bss
sock resq 0x1 ; サーバーソケット
clientfd resq 0x1 ; クライアントソケット
filefd resq 0x1
file_size resb 0x400 ; HTMLファイルサイズ
file_buf resb 0x20000 ; 128 KiB
req_buf resb 0x1000 ; 4 KiB
addr resb 0x10 ; sockaddr_in ストラクチャー
section .text
%include "file.s"
%include "u64todec.s"
global _start
_start:
mov rax, 4 ; sys_write
mov rdi, 1 ; stdout
mov rsi, listen_msg
mov rdx, listen_len
syscall
; ソケットの作成
mov rax, 97 ; sys_socket
mov rdi, 2 ; PF_INET
mov rsi, 1 ; SOCK_STREAM
mov rdx, 0 ; プロトコール
syscall
cmp rax, 0
jl error_exit
mov [sock], rax
; 0.0.0.0:8000 にバインド
mov word [addr], 2 ; sin_family = AF_INET
mov word [addr+2], 0x401f ; sin_port = 8000 (ポート番号)、ネットワークのバイト列0x1f40
;mov dword [addr+4], 0x0100007f ; sin_addr = 127.0.0.1(リトルエンディアンで)
mov dword [addr+4], 0 ; sin_addr = INADDR_ANY = 0.0.0.0
mov qword [addr+8], 0 ; パッディング
; バインド
mov rax, 104 ; sys_bind
mov rdi, [sock]
mov rsi, addr
mov rdx, 0x10
syscall
cmp rax, 0
jne error_exit
; リッスン
mov rax, 106 ; sys_listen
mov rdi, [sock]
mov rsi, 0xa ; バックログ
syscall
cmp rax, 0
jne error_exit
; HTMLファイルをメモリに読み込み一回だけ
call load_file
test rax, rax
jnz error_exit ; ファイルを見つけなければ、エラーで終了する
accept_loop:
; 接続の受け取り
; mov rax, 30 ; sys_accept
mov rax, 541 ; sys_accept4
mov rdi, [sock]
mov rsi, 0
mov rdx, 0
mov r10, 0 ; フラグ0
syscall
cmp rax, 0
jl loop_continue
mov [clientfd], rax
; リクエストの読み込み
mov rax, 3 ; sys_read
mov rdi, [clientfd]
mov rsi, req_buf
mov rdx, 0xfff
syscall
; ヘッダーの送信
; Content-Length文字から
mov rax, [file_size]
mov rdi, clen_str
call u64_to_dec
mov rax, 4 ; sys_write
mov rdi, [clientfd]
mov rsi, http_header
mov rdx, clen_str + 20 - http_header ; ヘッダーの長さCRLF含む
syscall
; ファイル内容の送信
mov rax, 4 ; sys_write
mov rdi, [clientfd]
mov rsi, file_buf
mov rdx, [file_size]
syscall
; クライアントの終了
mov rax, 6 ; sys_close
mov rdi, [clientfd]
syscall
loop_continue:
jmp accept_loop
error_exit:
mov rax, 1 ; sys_exit
mov rdi, 1
syscall
; 終了CTRL+C
; mov rax, 1 ; sys_exit
; xor rdi, rdi
; syscall

33
u64todec.s Normal file
View File

@@ -0,0 +1,33 @@
section .text
u64_to_dec:
mov rcx, 10
mov r8, rdi
lea rdi, [rdi + 0x13]
test rax, rax
jnz .convert
mov byte [rdi], '0'
dec rdi
jmp .pad
.convert:
xor rdx, rdx
div rcx
add dl, '0'
mov [rdi], dl
dec rdi
test rax, rax
jnz .convert
.pad:
inc rdi
.pad_loop:
cmp rdi, r8
jbe .done
mov byte [rdi], ' '
inc rdi
jb .pad_loop
.done:
ret

12
www/index.html Normal file
View File

@@ -0,0 +1,12 @@
<!DOCTYPE html>
<html lang="ja">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<link rel="stylesheet" type="text/css" href="/style.css" />
<title>ささ</title>
</head>
<body>
<h1>ささ</h1>
</body>
</html>

4
www/style.css Normal file
View File

@@ -0,0 +1,4 @@
body {
background-color: #232023;
color: #fcfcfc;
}