[Question]
  [
This is an adaption of [Core War](http://en.wikipedia.org/wiki/Core_War), a programming KOTH dating back to the 20th century. To be more specific, it is using an incredibly simplified instruction set primarily based off of the [original proposal](http://corewar.co.uk/cwg.txt).
## Background
In Core War, there are two programs battling for control over the computer. The goal of each program is to win by locating and terminating the opposing program.
The battle takes place within the main memory of the computer. This memory is called the Core, and it contains 8192 addresses. When the battle starts, the code for each competitor (called a warrior) is placed in a random chunk of memory. Program execution alternates between warriors, performing one instruction of each. Each instruction is capable of modifying a part of the Core, leading to the possibility of self-modifying programs.
The goal is to terminate the opposing program. A program terminates when it attempts to execute an invalid instruction, which is any `DAT` instruction.
# The Instruction Set
Each program consists of a series of low-level instructions, each of which takes two fields, called the A and B fields.
This instruction set draws heavily from the original spec. The main changes are 1) clarification on adding/subtracting commands, and 2) a change of the `#` addressing mode to allow it to be used anywhere. Most full versions of Core Wars have over 20 opcodes, 8 addressing modes, and a set of "instruction modifiers."
## Opcodes
Each instruction must have one of seven different opcodes.
* **`DAT A B`** - (data) - This simply holds the numbers `A` and `B`. Importantly, a process dies when it attempts to execute a DAT instruction.
* **`MOV A B`** - (move) - This moves the contents of memory location `A` to memory location `B`. Here is a demonstration of before-and-after:
```
MOV 2 1
ADD @4 #5
JMP #1 -1
```
```
MOV 2 1
JMP #1 -1
JMP #1 -1
```
* **`ADD A B`** - (add) - This adds the contents of memory location `A` to memory location `B`. The two first fields of both are added, and the second fields are added.
```
ADD 2 1
MOV @4 #5
JMP #1 -1
```
```
ADD 2 1
MOV @5 #4
JMP #1 -1
```
* **`SUB A B`** - (subtract) - This subtracts the contents of memory location `A` from (and stores the result into) memory location `B`.
```
SUB 2 1
MOV @4 #5
JMP #1 -1
```
```
SUB 2 1
MOV @3 #6
JMP #1 -1
```
* **`JMP A B`** - (jump) - Jump to location `A`, which will be executed next cycle. `B` must be a number but does nothing (you can use it to store information, though).
```
JMP 2 1337
ADD 1 2
ADD 2 3
```
The jump means that `ADD 2 3` will be executed next cycle.
* **`JMZ A B`** - (jump if zero) - If both fields of line `B` are 0, then the program jumps to location `A`.
```
JMZ 2 1
SUB 0 @0
DAT 23 45
```
Since the two fields of instruction 1 are 0, the DAT command will be executed next turn, leading to imminent death.
* **`CMP A B`** - (compare and skip if not equal) - If the fields in instructions `A` and `B` are not equal, skip the next instruction.
```
CMP #1 2
ADD 2 #3
SUB @2 3
```
Since the two fields of instructions 1 and 2 are equal in value, the ADD command is *not* skipped and is executed next turn.
When two instructions are added/subtracted, the two fields (A and B) are added/subtracted pair-wise. The addressing mode and opcode are not changed.
## Addressing Modes
There are three kinds of addressing modes. Each of the two fields of an instruction has one of these three addressing modes.
* **Immediate `#X`** - `X` is the line to be used directly in computation. For example, `#0` is the first line of the program. Negative lines refer to lines in the core before the start of program.
```
... //just a space-filler
...
ADD #3 #4
DAT 0 1
DAT 2 4
```
This will add the first of the two DAT lines to the second, since those are in lines 3 and 4, respectively. You would not want to use this code, however, because the DAT will kill your bot on the next cycle.
* **Relative `X`** - The number `X` represents the location of a target memory address, relative to the current address. The number at this location is used in computation. If line `#35` is being executed and contains `-5`, then line `#30` is used.
```
... //just a space-filler
...
ADD 2 1
DAT 0 1
DAT 2 4
```
This will add the second DAT line to the first.
* **Indirect `@X`** - The number `X` represent a relative address. The contents at that location are temporarily added to the number X to form a new relative address, from which the number is retrieved. If line `#35` is being executed, and its second field is `@4`, and the second field of line `#39` contains the number `-7`, then line `#32` is used.
```
... //just a space-filler
...
ADD @1 @1
DAT 0 1
DAT 2 4
```
This will add the first DAT to the second, but in a more convoluted way. The first field is @1, which gets the data from that relative address, which is the first field of the first DAT, a 0. This is interpreted as a second relative address from that location, so 1+0=1 gives the total offset from the original instruction. For the second field, @1 gets the value from that relative address (the 1 in the second field of the first DAT) and adds it to itself in the same way. The total offset is then 1+1=2. So, this instruction is executed similarly to `ADD 1 2`.
Each program can contain up to 64 instructions.
When a round starts, the two programs are placed randomly in a memory bank with 8192 locations. The instruction pointer for each program starts at the beginning of the program and is incremented after each execution cycle. The program dies once its instruction pointer attempts to execute a `DAT` instruction.
## Parameters of the Core
The core size is 8192, with a timeout of 8192\*8 = 65536 ticks. The core is cyclic, so writing to address 8195 is the same as writing to address 3. All unused addresses are initialized to `DAT #0 #0`.
Each competitor must not be longer than 64 lines. Integers will be stored as 32-bit signed integers.
## Parsing
In order to make programming easier for competitors, I will add a line-label feature to the parser. Any words that occur on a line before an opcode will be interpreted as line labels. For example, `tree mov 4 6` has the line label `tree`. If, anywhere in the program, there is a field that contains `tree` `#tree` or `@tree`, a number will be substituted. Also, capitalization is ignored.
Here is a example of how line labels are substituted:
```
labelA add labelB @labelC
labelB add #labelC labelC
labelC sub labelA @labelB
```
Here, labels A, B, and C are on lines 0, 1, and 2. Instances of `#label` will be substituted with the line number of the label. Instances of `label` or `@label` are substituted with the relative location of the label. Addressing modes are preserved.
```
ADD 1 @2
ADD #2 1
SUB -2 @-1
```
# Scoring
For each pair of contestants, every possible battle is performed. Since the outcome of a battle depends on the relative offsets of the two programs, every possible offset (about 8000 of them) is tried. Furthermore, each program has a chance to move first in each offset. The program that wins the majority of these offsets is the winner of the pair.
For each pair-up that a warrior wins, it is awarded 2 points. For each tie, a warrior is awarded 1 point.
You are allowed to submit more than one warrior. The typical rules for multiple submissions apply, such as no tag-teaming, no cooperating, no king-making, etc. There's not really any room for this in Core War anyways, so it shouldn't be a big deal.
# The Controller
The code for the controller, along with two easy example bots, [is located here](https://github.com/PhiNotPi/NanoCoreWar). Since this competition (when run using the official settings) is completely deterministic, the leaderboard you create will be the exact same as the official leaderboard.
## Example Bot
Here is an example bot that demonstrates some features of the language.
```
main mov bomb #-1
     add @main main
     jmp #main 0
bomb dat 0 -1
```
This bot operates by slowly erasing all other memory in the core by replacing it with a "bomb." Since the bomb is a `DAT` instruction, any program which reaches a bomb will be destroyed.
There are two line labels, "main" and "bomb" which serve to replace numbers. After preprocessing, the program looks like this:
```
MOV 3 #-1
ADD @-1 -1
JMP #0 0
DAT 0 -1
```
The first line copies the bomb to the line immediately above the program. The next line adds the value of the bomb (`0 -1`) to the move command, and it also demonstrates a use of the `@` addressing mode. This addition causes the move command to point to a new target. The next command unconditionally jumps back to the start of the program.
---
# Current Leaderboard
> 
> 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 - Slug 
> 
> 
> 
Pairwise Results:
```
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
```
The latest update (new versions of Turbo and Paranoid) took about 5 minutes to run on an old laptop. I would like to thank Ilmari Karonen for his improvements to [the controller](https://github.com/PhiNotPi/NanoCoreWar). If you have a local copy of the controller, you should update your files.
  
[Answer]
# Dwarven Engineer
A new and improved Dwarf. Wins against everything else submitted so far. The fancy [corestep](http://www.infionline.net/~wtnewton/corewar/corestep.c)-optimized step size is probably overkill here.
```
        MOV bomb    @aim
aim     MOV bomb    @-6326
        SUB step    aim
step    JMZ #0      6328
        MOV 0       1
bomb    DAT 0       3164
```
Notable features include the fast bombing loop that throws two bombs in four cycles, for an average bombing speed of 0.5c in old Core War jargon, and the use of `JMZ` to detect when the bombing run is complete and it's time to switch to plan B (here, an Imp).
---
I used to play Core War back in the 90's (some of you may have seen the basic [guidebook](http://vyznev.net/corewar/guide.html) I wrote back in '97), so I thought it would be interesting to see which old strategies from the RedCode '88 / '94 world might be useful in this variant.
My first thoughts were:
* There's no `SPL`, thus no replicators (and no imp rings/spirals). This should make bombers strong. (Also, all those fancy bombing strategies designed to deal with replicators and imp spirals? Totally needless and useless here. Just bomb with any `DAT`s.)
* Then again, `CMP` scanning is still potentially faster than bombing, so a fast scanner *could* have a chance.
* The absence of in/decrements makes core clears very slow. In fact, a core clear in this variant is pretty much just a bomber with a (suboptimal) step size of ±1. Again, this also hurts scanners; a one-shot scanner → bomber strategy *might* work, though.
* Quickscanners / quickbombers (an early-game strategy using an unrolled scanning / bombing loop, for those not so familar with Core War jargon) are still potentially useful, but only against long programs (which they themselves are, so there's a kind of a feedback effect here). Hard to say if it's really worth the trouble.
* The scoring system is interesting. Ties score half as much points as a win (rather than 1/3, as in traditional Core War), making them more attractive. Then again, about the only program likely to score lots of ties under these rules is an imp. (Also, the absence of de/increments makes imp gates hard, so even simple imps actually *do* have a chance of scoring a tie if they reach their opponent alive.)
* Also, because the final rankings only depend on which programs you beat, and not how *much* you beat them by, it tends to favor generalist entries. It's better to just barely beat *all* of your opponents, than to totally destroy half of them and just barely lose to the rest.
* Because the code is public, it's *always* possible to find a program that can beat any given earlier submission — possibly even several of them — no matter how good they are in general. Such tricks (like tuning your step size to hit your opponent just before they hit you) can easily seem cheap, though. And, of course, the target player could always just submit a new version with different constants.
Anyway, the upshot of all this is that I decided that I should try to write either a fast bomber or a *very* fast scanner, and *maybe* tack a quickscanner/bomber onto it. Out of those options, a fast bomber seemed the simplest and most likely to work.
At that point, I spent way too much time tweaking and optimizing PhiNotPi's interpreter code, because I figured I'd probably be running lots of brute force trials to optimize the constants. As it happens, I never had to do that — the code above is pretty much the first version that actually worked (after a couple of failed attempts that just committed suicide due to silly bugs).
---
The trick that makes my bomber fast is using indirect addressing to throw two bombs for each `ADD`. Here's how it work:
1. On the first cycle, we execute `MOV bomb @aim`. This copies the `bomb` instruction to whereever in the core the B-field of `aim` points to (initially, exactly 6326 instructions before `aim`, or 6328 instructions before `step`; you'll see why those numbers matter later).
2. On the next step, we execute the `aim` instruction itself! On the first pass, it looks like this: `MOV bomb @-6326`. Thus, it copies `bomb` to the location that the B-field of the instruction at 6326 lines before itself points to.
So, what is there at 6326 lines before `aim`? Why, it's the copy of `bomb` we just placed there one cycle earlier! And we just happened to arrange things so that the B-field of `bomb` has a non-zero value, so the new bomb will not be copied on top of the old one, but some distance away (in fact, here the distance is 3164, which is half of our nominal step size 6328; but other offsets could work, perhaps even better).
3. On the next cycle, we adjust our aim with `SUB step aim`, which subtracts the values of the `step` instruction (which also happens to be the jump we're going to execute next, although it *could've* been just a simple `DAT` somewhere) from `aim`.
(One detail to note here is that we *kind of* want the A-value of `step` to be zero, so that we'll still throw the same bombs on the next iteration. Even that isn't strictly necessary, though; only the bombs thrown by the *first* instruction need to have their B-field equal to 3164, the rest can be anything.)
4. Next, the `JMZ` check that the instruction 6328 steps away from it is still zero, and if so, jumps back to the top of the code. Now, 6328 is the step size of our bomber, and is divisible by 8 (but not 16); thus, if we just kept throwing bombs every 6328 steps, we'd eventually get back to where we started, having bombed every eighth instruction in the core (and with the extra bombs offset by 3163 = 6328/2 ≡ 4 (mod 8), we would've hit every *fourth* instruction).
But we started our bombing run at 6328 instructions *before* the `JMZ`, and stepped backwards by -6328 at every iteration, so we're going to bomb the location 6328 steps *after* the `JMZ` just one iteration before we would hit the `JMZ` itself. So when the `JMZ` detects a bomb at 6328 instructions after it, that's a sign that we've covered as much of the core as we can without hitting ourself, and should switch to a backup strategy before we kill ourself.
5. As for the backup strategy, it's just a plain old `MOV 0 1` imp, because I couldn't think of anything better for now. The way I see it, if we've bombed every fourth location of the core and still haven't won, we're probably fighting something very small or very defensive, and might as well just try to survive and settle for a tie. It's OK, because such small or defensive programs generally aren't very good at killing anything else, and so even if we only win a few fights by chance, we'll probably still come out ahead.
---
**Ps.** ~~In case anyone else wants it, here's my [slightly improved fork of PhiNotPi's tournament code](https://github.com/vyznev/NanoCoreWar). It's about twice as fast, saves old battle results so that you don't need to re-run them, and fixes what I believe to be [a minor bug in the battle results calculation.](https://github.com/PhiNotPi/NanoCoreWar/pull/2)~~ The changes have been merged into the [mainline version](https://github.com/PhiNotPi/NanoCoreWar) by PhiNotPi. Thanks!
[Answer]
# Turbo
```
main   add three target
test   jmz -1 @target
bomb   mov three @target
       sub j1 target 
       mov jump @target
       sub j1 target 
       mov copy @target
       sub j1 target
two    mov decr @target
j1     jmp @target 1
target dat -8 -8   
decr   sub #two 3
copy   mov 2 @2
jump   jmp -2 0
three dat -9 -9
```
My 2nd ever CoreWar attempt. Designed to beat Dwarf.
Scans by 3's for data, then puts a bomb every 2. Each stage runs in only 3 instructions, in a hope that Dwarf's bombs miss it.
**NEW Turbo++**: Now enhanced. It scans backward until it finds data, then moves itself there, then bombs backward. The hope is that the move either clobbers the opponent, or is to a place already bombed and therefore safe(ish).
...And an edit to make it scan more sparsely makes it beat everyone!
[Answer]
# Dwarf
A common and simple program that represents a dwarf throwing stones. It places a `DAT` instruction every four addresses.
```
add 2 3
mov 2 @2
jmp -2 #4
dat #0 #4
```
EDIT: Fixes addressing. Apparently the addressing modes are different from the spec the OP linked to.
[Answer]
# Graph View
This can be used as a debugging tool. It displays the core and shows the location of the player. To use it you have to call it from code. I have also provided a modifed `Game.java` that automatically displays the GraphView.
PhiNotPi and Ilmari Karonen recently changed the Controller. Ilmari Karonen has been kind enough to provide an updated GameView at [this location](https://github.com/vyznev/NanoCoreWar/tree/graphics).
```
import javax.swing.*;
import java.awt.*;
public class GameView extends JComponent{
    final static Color[] commandColors = new Color[]{
            Color.black, //DAT
            Color.blue,  //MOV
            Color.blue,  //ADD
            Color.blue,  //SUB
            Color.blue,  //JMP
            Color.blue,  //JMZ
            Color.blue,  //CMP
    };
    final static Color[] specialColors = new Color[]{
            new Color(0,0,0),
            new Color(190, 255, 152),
            Color.yellow,
            new Color(0, 93, 14),
            new Color(96, 92, 4),
            new Color(0, 93, 14),
            new Color(96, 92, 4),
            new Color(0, 93, 14),
            new Color(96, 92, 4)
    };
    final static Color playerOneColor = Color.green;
    final static Color playerTwoColor = Color.white;
    final Game game;
    int playerOneLocation;
    int playerTwoLocation;
    final static int width = 128;
    final static int height = 64;
    public GameView(Game game) {
        this.game = game;
    }
    @Override
    public void paint(Graphics g) {
        int pixelWidth = getSize().width;
        int pixelHeight = getSize().height;
        if (width > pixelWidth){
            pixelWidth = width;
            setSize(width, pixelHeight);
        }
        if (height > pixelHeight){
            pixelHeight = height;
            setSize(pixelWidth, height);
        }
        int squareWidth = Math.min(pixelWidth / width, pixelHeight / height);
        for (int x = 0; x < squareWidth * width; x += squareWidth){
            for (int y = 0; y < squareWidth * height; y += squareWidth){
                int index = (y / squareWidth) * width + (x / squareWidth);
                Color color = commandColors[game.core[index][0]];
                if (game.coreData[index] != 0){
                    color = specialColors[game.coreData[index]];
                }
                if (index == playerOneLocation){
                    color = playerOneColor;
                }
                if (index == playerTwoLocation){
                    color = playerTwoColor;
                }
                g.setColor(color);
                g.fillRect(x, y, squareWidth, squareWidth);
            }
        }
    }
    public void setLocations(int p1loc, int p2loc){
        this.playerOneLocation = p1loc;
        this.playerTwoLocation = p2loc;
    }
}
```
Modified Game.java:
```
import javax.swing.*;
import java.util.Random;
import java.util.ArrayList;
import java.util.Arrays;
/**
 * This runs a game of Core Wars between two players.  It can be called mutiple times.
 * 
 * @author PhiNotPi 
 * @version 3/10/15
 */
public class Game
{
    final Player p1;
    final Player p2;
    final int coreSize;
    final int coreSizeM1;
    final int maxTime;
    final int debug;
    public int[][] core;
    public int[] coreData; //Used in debugging.
    int offset1;
    int offset2;
    Random rand;
    ArrayList<int[]> p1code;
    ArrayList<int[]> p2code;
    int p1size;
    int p2size;
    GameView gameView;
    int time = 1000000; //Time in nanoseconds between frames
    public Game(Player A, Player B, int coreSize, int maxTime, int debug)
    {
        p1 = A;
        p2 = B;
        
        coreSize--;
        coreSize |= coreSize >> 1;
        coreSize |= coreSize >> 2;
        coreSize |= coreSize >> 4;
        coreSize |= coreSize >> 8;
        coreSize |= coreSize >> 16;
        coreSize++;
        
        this.coreSize = coreSize;
        this.coreSizeM1 = coreSize - 1;
        this.maxTime = maxTime / 2;
        this.debug = debug;
        core = new int[coreSize][5];
        rand = new Random();
        p1code =  p1.getCode();
        p1size = p1code.size();
        p2code =  p2.getCode();
        p2size = p2code.size();
        if (debug == 1){
            gameView = new GameView(this);
            JFrame frame = new JFrame("Game");
            frame.add(gameView);
            frame.setVisible(true);
            frame.setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE);
            frame.setSize(128, 64);
            coreData = new int[coreSize];
        }
    }
    
    public int runAll()
    {
        int sum = 0;
        for(int i = 0; i < coreSize - p1size - p2size; i++)
        {
            sum += run(i) - 1;
        }
        if(sum > 0)
        {
            return 1;
        }
        if(sum < 0)
        {
            return -1;
        }
        return 0;
    }
    
    public int run()
    {
        return run(rand.nextInt(coreSize - p1size - p2size + 1));
    }
    
    public int run(int deltaOffset)
    {
        core = new int[coreSize][5];
        //offset1 = rand.nextInt(coreSize);
        offset1 = 0;
        for(int i = 0; i != p1size; i++)
        {
            //System.arraycopy(p1.getCode().get(i), 0, core[(offset1 + i) % coreSize], 0, 5 );
            int[] line = p1code.get(i);
            int loc = (offset1 + i) & coreSizeM1;
            core[loc][0] = line[0];
            core[loc][1] = line[1];
            core[loc][2] = line[2];
            core[loc][3] = line[3];
            core[loc][4] = line[4];
            if (debug != 0){
                coreData[loc] = 1;
            }
        }
        offset2 = offset1 + p1size + deltaOffset;
        for(int i = 0; i != p2size; i++)
        {
            //System.arraycopy(p2.getCode().get(i), 0, core[(offset2 + i) % coreSize], 0, 5 );
            int[] line = p2code.get(i);
            int loc = (offset2 + i) & coreSizeM1;
            core[loc][0] = line[0];
            core[loc][1] = line[1];
            core[loc][2] = line[2];
            core[loc][3] = line[3];
            core[loc][4] = line[4];
            if (debug != 0){
                coreData[loc] = 2;
            }
        }
             
        int p1loc = offset1 & coreSizeM1;
        int p2loc = offset2 & coreSizeM1;
        for(int time = 0; time != maxTime; time++)
        {
            if(debug != 0)
            {
                //printCore(p1loc,p2loc);
                //System.out.println("p1loc " + p1loc);
                //System.out.println("offset " + offset1);
                gameView.setLocations(p1loc, p2loc);
                gameView.repaint();
                try {
                    Thread.sleep(time / 1000000, time % 1000000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
            
            if(core[p1loc][0] == 0)
            {
                return 0;
            }
            p1loc = execute(p1loc, offset1, 1);
            
            if(debug != 0)
            {
                //printCore(p1loc,p2loc);
                //System.out.println("p2loc " + p2loc);
                //System.out.println("offset " + offset2);
                gameView.setLocations(p1loc, p2loc);
                gameView.repaint();
                /*try {
                    Thread.sleep(time);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }*/
            }
            if(core[p2loc][0] == 0)
            {
                return 2;
            }
            p2loc = execute(p2loc, offset2, 2);
            
        }
        return 1;
    }
    public int execute(int ploc, int offset, int player)
    {
        int line1 = offset + core[ploc][3];
        if(core[ploc][1] != 0)
        {
            line1 += ploc - offset;
        }
        if(core[ploc][1] == 2)
        {
            line1 += core[line1 & coreSizeM1][3];
        }
        int line2 = offset + core[ploc][4];
        if(core[ploc][2] != 0)
        {
            line2 += ploc - offset;
        }
        if(core[ploc][2] == 2)
        {
            line2 += core[line2 & coreSizeM1][4];
        }
        line1 = line1 & coreSizeM1;
        line2 = line2 & coreSizeM1;
        int opcode = core[ploc][0];
        ploc = (ploc + 1) & coreSizeM1;
        //String opDescription = "";
        if(opcode == 1)
        {
            core[line2][0] = core[line1][0];
            core[line2][1] = core[line1][1];
            core[line2][2] = core[line1][2];
            core[line2][3] = core[line1][3];
            core[line2][4] = core[line1][4];
            if (debug != 0) {
                coreData[line2] = player + 2;
            }
            return ploc;
            //opDescription = "Moved from " + line1 + " to " + line2;
        }
        if(opcode == 2)
        {
            core[line2][3] += core[line1][3];
            core[line2][4] += core[line1][4];
            if (debug != 0) {
                coreData[line2] = player + 4;
            }
            return ploc;
            //opDescription = "Added " + line1 + " to " + line2;
        }
        if(opcode == 3)
        {
            core[line2][3] -= core[line1][3];
            core[line2][4] -= core[line1][4];
            if (debug != 0) {
                coreData[line2] = player + 6;
            }
            return ploc;
                //opDescription = "Subtracted " + line1 + " to " + line2;
        }
        if(opcode == 4)
        {
            ploc = line1;
            return ploc;
                //opDescription = "Jumped to " + line1;
        }
        if(opcode == 5)
        {
                if(core[line2][3] == 0 && core[line2][4] == 0)
                {
                    ploc = line1;
                    //opDescription = "Jumped to " + line1;
                }
                else
                {
                    //opDescription = "Did not jump to " + line1;
                }
                return ploc;
        }
        if(opcode == 6)
        {
            if(core[line1][3] == core[line2][3] && core[line1][4] == core[line2][4])
            {
                //opDescription = "Did not skip because " + line1 + " and " + line2 + " were equal.";
            }
            else
            {
                ploc = (ploc + 1) & coreSizeM1;
                //opDescription = "Skipped because " + line1 + " and " + line2 + " were not equal.";
            }
            return ploc;
        }
        if(debug != 0)
        {
            //System.out.println(opDescription);
        }
        return ploc;
    }
    /*public void printCore(int p1loc, int p2loc)
    {
        int dupCount = 0;
        int[] dupLine = new int[]{0,0,0,0,0};
        for(int i = 0; i < core.length; i++)
        {
            int[] line = core[i];
            if(Arrays.equals(line, dupLine) && i != p1loc && i != p2loc)
            {
                if(dupCount == 0)
                {
                    System.out.println(Player.toString(line));
                }
                dupCount++;
            }
            else
            {
                if(dupCount == 2)
                {
                    System.out.println(Player.toString(dupLine));
                }
                else if(dupCount > 2)
                {
                    System.out.println("    " + (dupCount - 1) + " lines skipped.");
                }
                System.out.println(Player.toString(line));
                if(i == p1loc)
                {
                    System.out.print(" <- 1");
                }
                if(i == p2loc)
                {
                    System.out.print(" <- 2");
                }
                dupLine = line;
                dupCount = 1;
            }
        }
        if(dupCount == 2)
        {
            System.out.println(Player.toString(dupLine));
        }
        else if(dupCount > 2)
        {
            System.out.println("    " + (dupCount - 1) + " lines skipped.");
        }
    }*/
}
```
[Answer]
# Evolved
~~I honestly don't get how it works. It seems to construct its source code before doing anything. I would love it if someone gave me an explanation for how it works.~~
After studying it, I found that it is simply a modified dwarf with an imp guard. Instead of bombing the enemies with `DAT` instructions, it shuffles the enemies code. It also bombs every two registers instead of every four registers. Given enough time, it would undoubtedly destroy itself.
```
MOV -2 #-1
MOV #4 -9
SUB -5 #6
MOV #1 1
MOV #-6 #4
SUB @8 @7
JMP -3 @4
DAT #-4 8
JMP -1 9
JMP 5 #-10
CMP @-1 #0
SUB 3 #-10
JMP @10 #-9
JMZ #1 10
MOV #3 2
ADD @9 @-3
CMP #-3 @7
DAT @0 @-2
JMP @-7 #6
DAT @-8 -6
MOV @0 #9
MOV #2 1
DAT @6882 #-10
JMP @3 4
CMP @8 2
ADD -7 @11
ADD @1 #-9
JMZ @-5 7
CMP 11 5526
MOV @8 6
SUB -6 @0
JMP 1 11
ADD @-3 #-8
JMZ @-14 @-5
ADD 0 @-8
SUB #3 @9
JMP #-1 5
JMP #9 @1
CMP -9 @0
SUB #4 #-2
JMP #-8 5
DAT -1 @-10
MOV 6 #2
CMP @-11 #-14
ADD @4 @-3
MOV @5 #-6
SUB -3 -2
DAT @-10 #-1
MOV #-13 #-6
MOV #1 5
ADD 5 #-5
MOV -8 @-1
DAT 0 10
DAT #5 #7
JMZ 6 -5
JMZ -12 -11
JMP 5 @-7
MOV #7 -3
SUB #-7 @-3
JMP -4 @-11
CMP @-5 #-2
JMZ @-1 #0
ADD #3 #2
MOV #5 @-6
```
[Answer]
# CopyPasta
Never participated to a CoreWar, this simple program is just trying to copy-paste himself and then execute the copy. It may not have the correct behavior, please tell me if it is the case.
It is too pacifist and can't win in fact.
```
MOV 6 0
MOV @-1 @-1
CMP @-2 3
JMP 4242 0
SUB -3 -4
JMP -4 0
DAT 0 4244
```
[Answer]
# FirstTimer
If it does work, it should try to take position at the start of the core and create a defens
```
main MOV 5 #0
     ADD #data #main
     CMP #main #max
     JMP #0 0
     JMP #main 0
     MOV #data #100
     ADD #data -1
     JMP -2 0
data DAT 1 1
max  DAT 8 3
```
[Answer]
# Janitor
It should check if the following addresses are empty and if not it cleans them (thus, hopefully, erasing the opponent bot).
**Edit:** This new version should be quicker (now that I understood the `JMZ` command and the `@` reference correctly).
```
JMZ 2 6
MOV 4 @-1
ADD 2 -2
JMP -3 0
DAT 0 1
DAT 0 0
```
[Answer]
# ScanBomber
Remove my comments before compiling. Scans for a while, then bombs when it finds a program. It probably will still lose to my Dwarf, though.
```
scan add #eight #range  ; scan
jmz #scan @range
sub #six #range
fire mov #zero @range   ; bombs away! (-6)
add #two #range
mov #zero @range
add #two #range
mov #zero @range
add #two #range
mov #zero @range        ; (+0)
add #two #range
mov #zero @range
add #two #range
mov #zero @range
add #two #range
mov #zero @range
add #two #range
mov #zero @range        ; (+8)
range jmp #scan 6
two dat 0 2
six dat 0 6
zero dat 0 0
eight dat 0 8
```
[Answer]
# Han Shot First (v2)
I figured the competition could use some more diversity, so here's my second entry: a one-shot `CMP` scanner.
This is **version 2**, with improved anti-Imp defenses — it can now beat Imp, if only by just one point. It still loses to Dwarven Engineer, but beats everything else so far, putting it currently in tied first place.
```
scan    ADD bomb    aim
aim     CMP 17      12
        JMZ scan    #-3
loop    MOV bomb    @aim
        ADD step    aim
step    JMP loop    #2
bomb    DAT 10      10
```
It works by comparing adjacent core locations 5 steps apart, at 10-step intervals, until it finds a difference. When it does, it starts throwing bombs at 2-step intervals until it kills its opponent or loops all the way around the core to reach itself.
If the scan does *not* find anything else, it will eventually loop around and find its own code and attack it. This would be suicidal, but for the fortunate coincidence that the first bomb lands squarely on the `aim` line, causing the next bomb to be thrown 12 positions (rather than the usual 2) down the core, conveniently skipping the code. (This also happens with 50% probability if the scan does find something, but fails to kill the opponent.) Since the core size is a multiple of two, this will also keep happening if the bombing run loops around, eliminating the need for a further backup strategy.
(This self-bombing trick was originally a pure coincidence — I had planned for a completely different way to switch from scanning to bombing mode if nothing was found, but when I first tested the code, the constants just happened to be right to make it work this way, and I decided to stick with it.)
[Answer]
# Imp
```
MOV 0 1
```
Simply inches through the program.
[Answer]
# Slug
```
     mov    ones    @-1024
     mov    from    -3
     mov    here    -3
loop mov    @-5 @-4
     add    ones  -5
     jmz    -17 -6
     add    ones  -8    
     jmp    loop    42
ones dat    1   1
from dat    2   2
here dat    -11 -11
```
Crawls through memory space backwards. Occasionally throws a bomb far away.
[Answer]
# Paranoid
Kind of a copy-pasta but it will check if the code have been modified by bombing. If so it copy past a dwarf and execute it. If I manage to make the GameView again I'll try to change some of the constants.
```
copy    MOV data copy
loop    MOV @-1 @-1
    CMP @copy end
out JMP check 0
    SUB loop copy
    JMP loop 0
data    DAT 0 4109
check   MOV data copy
loop2   CMP @copy @copy
    JMP ok 0
    MOV aah 2
ok  CMP @copy end
    JMP 4098 0
    SUB loop copy
    JMP loop2 0
panic   MOV end copy
    MOV jump out
    JMP loop 0
jump    JMP 4124 0
dwarf   ADD 2 bomb
    MOV bomb @bomb
    JMP dwarf 4
bomb    DAT 0 4
aah JMP 3 0
end DAT 19 4127
```
[Answer]
# Easter Bunny
He enjoys hopping backwards :)
```
loop mov 0 -10
     add data loop
     cmp -7 data
     jmp -13 0
     jmp loop 0
data dat 1 1
```
]