이것은 20 세기로 거슬러 올라가는 KOTH 프로그램 인 Core War에 대한 적응입니다 . 보다 구체적으로, 그것은 원래 제안에 기초하여 매우 단순화 된 명령 세트를 사용하고 있습니다.
배경
Core War에는 컴퓨터를 제어하기 위해 싸우는 두 가지 프로그램이 있습니다. 각 프로그램의 목표는 반대 프로그램을 찾아 종료함으로써 승리하는 것입니다.
전투는 컴퓨터의 메인 메모리 내에서 이루어집니다. 이 메모리를 코어라고하며 8192 개의 주소가 포함되어 있습니다. 전투가 시작되면 각 경쟁자 (전사라고 함)의 코드가 임의의 메모리 덩어리에 배치됩니다. 프로그램 실행은 전사마다 번갈아 가며 각각의 명령을 수행합니다. 각 명령은 Core의 일부를 수정할 수 있으므로 자체 수정 프로그램이 가능합니다.
목표는 반대 프로그램을 종료하는 것입니다. 프로그램이 유효하지 않은 명령 (모든 DAT
명령) 을 실행하려고하면 종료됩니다 .
명령어 세트
각 프로그램은 일련의 하위 레벨 명령으로 구성되며 각 명령에는 A 및 B 필드라는 두 개의 필드가 필요합니다.
이 인스트럭션 세트는 원래 사양과 크게 다릅니다. 주요 변경 사항은 1) 명령 추가 / 빼기에 대한 설명 및 2) #
어드레싱 모드를 어디에서나 사용할 수 있도록 변경하는 것입니다 . 대부분의 Core Wars 버전에는 20 개가 넘는 opcode, 8 개의 주소 지정 모드 및 일련의 "명령 수정 자"가 있습니다.
오피 코드
각 명령어에는 7 개의 서로 다른 opcode 중 하나가 있어야합니다.
DAT A B
- (데이터) - 이것은 단순히 숫자를 보유A
하고B
. 중요한 것은 프로세스가 DAT 명령을 실행하려고 할 때 죽는 것입니다.MOV A B
-(이동)-메모리 위치의 내용을 메모리 위치A
로 옮깁니다B
. 이전과 이후의 데모는 다음과 같습니다.MOV 2 1 ADD @4 #5 JMP #1 -1
MOV 2 1 JMP #1 -1 JMP #1 -1
ADD A B
-(추가)-메모리 위치의 내용을 메모리 위치A
에 추가합니다B
. 두 필드 중 첫 번째 두 필드가 추가되고 두 번째 필드가 추가됩니다.ADD 2 1 MOV @4 #5 JMP #1 -1
ADD 2 1 MOV @5 #4 JMP #1 -1
SUB A B
-(빼기)-메모리 위치A
에서 메모리 위치의 내용을 빼고 결과를 메모리 위치에 저장합니다B
.SUB 2 1 MOV @4 #5 JMP #1 -1
SUB 2 1 MOV @3 #6 JMP #1 -1
JMP A B
-(점프)-위치로 이동하여A
다음 사이클에서 실행됩니다.B
숫자 여야하지만 아무것도하지 않습니다 (정보를 저장하는 데 사용할 수 있음).JMP 2 1337 ADD 1 2 ADD 2 3
점프는
ADD 2 3
다음 사이클에서 실행될 것임을 의미합니다 .JMZ A B
-(0 인 경우 점프)-두 행의 필드가 모두B
0이면 프로그램이 location으로 이동합니다A
.JMZ 2 1 SUB 0 @0 DAT 23 45
명령 1의 두 필드가 0이므로 DAT 명령이 다음 차례에 실행되어 임박한 사망으로 이어집니다.
CMP A B
- (비교하고 동일하지 않을 경우 생략) - 지시 필드 경우A
와는B
동일하지, 다음 명령을 건너 뜁니다.CMP #1 2 ADD 2 #3 SUB @2 3
명령어 1과 2의 두 필드는 값이 같으므로 ADD 명령은 건너 뛰지 않으며 다음 번에 실행됩니다.
두 개의 명령어를 더하거나 빼면 두 필드 (A와 B)가 한 쌍씩 더해집니다. 주소 지정 모드와 opcode는 변경되지 않습니다.
주소 지정 모드
주소 지정 모드에는 세 가지 종류가 있습니다. 명령어의 두 필드 각각에는이 세 가지 주소 지정 모드 중 하나가 있습니다.
즉시
#X
-X
계산에 직접 사용될 라인입니다. 예를 들어,#0
프로그램의 첫 번째 줄입니다. 네거티브 라인은 프로그램 시작 전 코어의 라인을 나타냅니다.... //just a space-filler ... ADD #3 #4 DAT 0 1 DAT 2 4
두 줄의 첫 번째 줄이 두 번째 줄에 추가됩니다. 두 줄은 각각 줄 3과 4에 있기 때문입니다. 그러나 DAT가 다음주기에 봇을 죽일 것이기 때문에이 코드를 사용하고 싶지 않습니다.
상대
X
-숫자X
는 현재 주소를 기준으로 대상 메모리 주소의 위치를 나타냅니다. 이 위치의 숫자는 계산에 사용됩니다. line#35
이 실행 중이고를 포함-5
하면 line#30
이 사용됩니다.... //just a space-filler ... ADD 2 1 DAT 0 1 DAT 2 4
두 번째 DAT 줄이 첫 번째 줄에 추가됩니다.
간접
@X
-숫자X
는 상대 주소를 나타냅니다. 해당 위치의 내용은 숫자 X에 임시로 추가되어 새로운 상대 주소를 형성하며, 이로부터 숫자를 검색합니다. line#35
이 실행 중이고 두 번째 필드가@4
이고 두 번째 필드가#39
number를 포함하면-7
line#32
이 사용됩니다.... //just a space-filler ... ADD @1 @1 DAT 0 1 DAT 2 4
이렇게하면 첫 번째 DAT가 두 번째에 추가되지만 더 복잡한 방식으로 추가됩니다. 첫 번째 필드는 @ 1이며 첫 번째 DAT의 첫 번째 필드 인 상대 주소에서 0을 가져옵니다.이 위치에서 두 번째 상대 주소로 해석되므로 1 + 0 = 1은 원래 명령에서 오프셋. 두 번째 필드의 경우 @ 1은 해당 상대 주소 (첫 번째 DAT의 두 번째 필드에있는 1)에서 값을 가져와 같은 방식으로 자체에 추가합니다. 총 오프셋은 1 + 1 = 2입니다. 따라서이 명령어는와 비슷하게 실행됩니다
ADD 1 2
.
각 프로그램은 최대 64 개의 명령어를 포함 할 수 있습니다.
라운드가 시작되면 두 프로그램은 8192 개의 위치가있는 메모리 뱅크에 무작위로 배치됩니다. 각 프로그램의 명령 포인터는 프로그램 시작시 시작되며 각 실행주기 후에 증가합니다. 명령 포인터가 DAT
명령 실행을 시도하면 프로그램이 종료 됩니다.
핵심의 매개 변수
코어 크기는 8192이며 시간 제한은 8192 * 8 = 65536 틱입니다. 코어는 주기적이므로 주소 8195에 쓰는 것은 주소 3에 쓰는 것과 같습니다 DAT #0 #0
. 사용하지 않는 모든 주소는로 초기화됩니다 .
각 경쟁 업체는 64 줄을 넘지 않아야합니다. 정수는 부호있는 32 비트 정수로 저장됩니다.
파싱
경쟁 업체의 프로그래밍을 쉽게하기 위해 파서에 라인 레이블 기능을 추가하겠습니다. opcode 앞의 줄에 나오는 단어는 줄 레이블로 해석됩니다. 예를 들어 tree mov 4 6
라인 레이블이 tree
있습니다. 프로그램의 어느 곳에 tree
#tree
나 또는 이 포함 된 필드가 있으면 @tree
숫자가 대체됩니다. 또한 대문자는 무시됩니다.
다음은 라인 레이블을 대체하는 방법의 예입니다.
labelA add labelB @labelC
labelB add #labelC labelC
labelC sub labelA @labelB
여기서 레이블 A, B 및 C는 줄 0, 1 및 2에 있습니다. 인스턴스 #label
는 레이블의 줄 번호로 대체됩니다. 라벨의 상대 위치 label
또는 인스턴스로 @label
대체됩니다. 주소 지정 모드가 유지됩니다.
ADD 1 @2
ADD #2 1
SUB -2 @-1
채점
각 참가자 쌍마다 가능한 모든 전투가 수행됩니다. 전투 결과는 두 프로그램의 상대적인 오프셋에 의존하기 때문에 가능한 모든 오프셋 (약 8000 개)이 시도됩니다. 또한 각 프로그램은 각 오프셋에서 먼저 이동할 수 있습니다. 이 오프셋의 대부분을 차지하는 프로그램이 쌍의 승자입니다.
전사가 승리 할 때마다 2 점을 얻습니다. 동점마다 1 점을 얻는다.
둘 이상의 전사를 제출할 수 있습니다. 태그 팀 구성, 협력 금지, 왕 제작 금지 등과 같은 다중 제출에 대한 일반적인 규칙이 적용됩니다. 어쨌든 Core War에는 실제로 이러한 공간이 없기 때문에 큰 문제가되지 않습니다.
컨트롤러
컨트롤러에 대한 코드는 2 개의 쉬운 예제 봇과 함께 여기에 있습니다 . 이 경쟁 (공식 설정을 사용하여 실행할 때)은 완전히 결정적이므로 생성 한 리더 보드는 공식 리더 보드와 정확히 동일합니다.
봇 예
다음은 언어의 일부 기능을 보여주는 봇 예제입니다.
main mov bomb #-1
add @main main
jmp #main 0
bomb dat 0 -1
이 봇은 코어의 다른 모든 메모리를 "폭탄"으로 교체하여 천천히 지 웁니다. 폭탄은 DAT
명령 이므로 폭탄에 도달하는 모든 프로그램은 파괴됩니다.
숫자를 대체하는 "main"과 "bomb"의 두 가지 라인 레이블이 있습니다. 전처리 후 프로그램은 다음과 같습니다.
MOV 3 #-1
ADD @-1 -1
JMP #0 0
DAT 0 -1
첫 번째 줄은 폭탄을 프로그램 바로 위의 줄에 복사합니다. 다음 줄 0 -1
은 이동 명령에 폭탄 값 ( )을 추가 하고 @
주소 지정 모드를 사용하는 방법도 보여줍니다 . 이 추가로 이동 명령이 새 대상을 가리 킵니다. 다음 명령은 무조건 프로그램 시작으로 되돌아갑니다.
현재 리더 보드
24-Turbo
22-DwarvenEngineer
20-HanShotFirst
18-Dwarf
14-ScanBomber
10-Paranoid
10-FirstTimer
10-Janitor
10-Evolved
6-EasterBunny
6-CopyPasta
4-Imp
2-슬러그
쌍별 결과 :
Dwarf > Imp
CopyPasta > Imp
Evolved > Imp
FirstTimer > Imp
Imp > Janitor
Imp > ScanBomber
Slug > Imp
DwarvenEngineer > Imp
HanShotFirst > Imp
Turbo > Imp
EasterBunny > Imp
Paranoid > Imp
Dwarf > CopyPasta
Dwarf > Evolved
Dwarf > FirstTimer
Dwarf > Janitor
Dwarf > ScanBomber
Dwarf > Slug
DwarvenEngineer > Dwarf
HanShotFirst > Dwarf
Turbo > Dwarf
Dwarf > EasterBunny
Dwarf > Paranoid
Evolved > CopyPasta
FirstTimer > CopyPasta
Janitor > CopyPasta
ScanBomber > CopyPasta
CopyPasta > Slug
DwarvenEngineer > CopyPasta
HanShotFirst > CopyPasta
Turbo > CopyPasta
CopyPasta > EasterBunny
Paranoid > CopyPasta
Evolved > FirstTimer
Evolved > Janitor
ScanBomber > Evolved
Evolved > Slug
DwarvenEngineer > Evolved
HanShotFirst > Evolved
Turbo > Evolved
EasterBunny > Evolved
Paranoid > Evolved
Janitor > FirstTimer
ScanBomber > FirstTimer
FirstTimer > Slug
DwarvenEngineer > FirstTimer
HanShotFirst > FirstTimer
Turbo > FirstTimer
FirstTimer > EasterBunny
FirstTimer > Paranoid
ScanBomber > Janitor
Janitor > Slug
DwarvenEngineer > Janitor
HanShotFirst > Janitor
Turbo > Janitor
Janitor > EasterBunny
Janitor > Paranoid
ScanBomber > Slug
DwarvenEngineer > ScanBomber
HanShotFirst > ScanBomber
Turbo > ScanBomber
ScanBomber > EasterBunny
ScanBomber > Paranoid
DwarvenEngineer > Slug
HanShotFirst > Slug
Turbo > Slug
EasterBunny > Slug
Paranoid > Slug
DwarvenEngineer > HanShotFirst
Turbo > DwarvenEngineer
DwarvenEngineer > EasterBunny
DwarvenEngineer > Paranoid
Turbo > HanShotFirst
HanShotFirst > EasterBunny
HanShotFirst > Paranoid
Turbo > EasterBunny
Turbo > Paranoid
Paranoid > EasterBunny
최신 업데이트 (Turbo 및 Paranoid의 새 버전)는 오래된 랩톱에서 실행하는 데 약 5 분이 걸렸습니다. Ilmari Karonen 이 컨트롤러 를 개선해 주셔서 감사 합니다 . 컨트롤러의 로컬 사본이있는 경우 파일을 업데이트해야합니다.