Como ya os comentamos en –> https://elbinario.net/2019/11/27/torneo-corewar/ tenemos en mente un torneo de CoreWar y como sabemos que RedCode y ASM puede ser un poco ladrillo y nos gustaría que todas las personas que estuvieran interesadas pudieran participar, vamos a ir desarrollando poco a poco algunas nociones básicas de RedCode para que podáis programar vuestros propios bichos, pero vamos de poco a poco, primero necesitamos nuestro tablero de juego que en nuestro caso es el simulador pmars.
Compilando Pmars
Bajamos la ultima versión de aquí –> https://sourceforge.net/projects/corewar/files/pMARS/
También podemos usar el repositorio de MD en github https://gitlab.com/tres-14159/corewar quien se ha encargado de limpiar «basurilla» del codigo original.
Una vez descomprimida la carpeta accedemos al directorio src y compilamos:
make
El core
El core es el tablero donde nuestros warriors compiten el core esta compuesto de una matriz de 8000 direcciones en forma de anillo que sirve de campo de batalla para nuestros procesos , el programa llena el core de ceros, antes de que los procesos de los warriors sean cargados en el, los warriors solo pueden lanzar un proceso a la vez, pero como el pmars es multitarea estos pueden dividirse. Cuando todos los procesos generados por un warrior han sido destruidos se considera muerto a ese warrior, cuando solo queda un warrior en el core, se le nombra a este ganador.
Bien ahora ya conocemos nuestro tablero de juego y las reglas, necesitamos crear las fichas, para ello tenemos que crear nuestros warriors,(hay un par de ejemplos en la carpeta de pmars, pero son avanzados y mejor los dejamos para luego)
Para construir nuestros warriors, usaremos redcode.
Redcode
Redcode es similar al lenguaje ensamblador, pero ligeramente distinto, redcode es un estilo de lenguaje ensamblador, algunas de las instrucciones de redcode son las siguientes:
DAT -- data (kills the process)
MOV -- mover (copia datos de la posicion actual a la siguiente)
ADD -- suma (suma un numero a otro)
SUB -- resta (resta un numero de otro)
MUL -- multiplica (multiplica un numero con otro)
DIV -- divide (divides un numero con otro)
MOD -- modulo (obtiene el resto de una division)
JMP -- salta (salta la ejecucion del programa a otra dirección )
JMZ -- salta si es cero
JMN -- salta si no es cero (
NOP -- no operacion
The Imp
Imp, también llamado trasgo es el primer programa warrior que se implemento en redcode por Alexander_Dewdney, su código es muy sencillo:
;redcode
;name Imp
;author A.K. Dewdney
;assert 1
imp mov imp,imp+1
end imp
Este es el código original,pero esta lleno de tags y etiquetas por lo que para para explicar mejor usaremos este otro:
mov 0,1
end
El código utiliza la instrucción mov, para copiarse de la posición actual(0) a la siguiente(1), nada mas este warrior solo avanza posiciones de memoria y crea copias de si mismo, no puede destruir a un oponente solo sobrevivir(que no es poco ;) . En las batallas de corewar el objetivo es destruir al enemigo pero el combate puede acabar de dos formas: -Empate: Ninguno de los oponentes consigue destuir al otro durante las rondas declaradas. -Ganador: El personajeX consigue destruir a su oponente, hay muchas maneras de hacerlo, pero en definitiva lo que que tenemos que hacer es que nuestro oponente ejecute una instrucción DAT el Imp necesita estar combinado con otros métodos para poder destruir al oponente,que ya veremos mas adelante, como por ejemplo lanzar un bombardeo de instrucciones DAT para que nuestro oponente las ejecute .
De momento vamos a testear nuestro Imp, para que veamos de manera visual como funciona, para ello creamos dos archivos en la carpeta warriors de pmars con nombre imp.red y trasgo.red y podemos lo siguiente:
;name imp
;assert CORESIZE==8000
mov 0,1
;name trasgo
;assert CORESIZE==8000
mov 0,1
Los guardamos y ejecutamos pmars con tres rondas(-r) hay muchos parámetros de pmars que podemos encontrar en https://manpages.ubuntu.com/manpages/eoan/man6/pmars.6.html:
./pmars -r 3 ../warriors/imp.red ../warriors/trasgo.red
y nos mostrara la siguiente pantalla, que vamos a detallar.
- Margen superior: Aparece el nombre de nuestros warriors, el que le hallamos puesto internamente en nuestro fichero .red así como su color asignado
- Rectángulo central: Es nuestro campo de batalla el core de pmars con sus 8000 direcciones de memoria, cada proceso va escribiendo su código en cada bit y se marca con su color
- Margen inferior: Se muestra el P-SPACE que es un área privada de memoria que tienen los warriors(hablaremos mas adelante) y opciones de debug.
Una vez terminadas las rondas, si pulsamos cualquier tecla nos aparecera en nuestro terminal algo como lo siguiente:
En el resumen podemos ver el código que ha ejecutado cada uno de los warriors, y el resultado final del combate que evidentemente es un empate, puesto que cada proceso, se va copiando a si mismo, por lo que habría que poner muchas rondas, para que un warrior, pisara una zona de memoria del core que ya ha sido escrita por otro warrior.
Os dejamos una pregunta para casa ¿que creéis que pasara si uno de los warriors utiliza mov para copiarse en zonas de memoria por detrás de su posición? ¿como quedara la batalla?
En el siguiente articulo veremos algo mas de acción, puesto que empezaremos a ver instrucciones de ataque, para no salir corriendo de todas las batallas. XDD
Happy hacking
Hola Puppetmaster,
He descargado, descomprimido, compilado, creado los dos archivos, copiado los textos…
Pero no consigo ejecutar en la terminal «./pmars -r 3 ../warriors/imp.red ../warriors/trasgo.red»
Indica: «no existe el archivo o directorio»
Alguna ayuda/consejo, please
Nas
¿Estas en la carpeta src cuando ejecutas el comando? –> pmars-0.9.2/src/ ¿Tienes los warriors situados con su extension .red en la carpeta pmars-0.9.2/warriors ? Realmente los warriors puedes situarlos en cualquier lado solo tienes que indicarle la ruta a pmars, el binario de pmars se encuentra en la carpeta src, una vez compilado con make.
Espero que te sirva ;) un saludo.
Me vais a matar pero hay una implementación de la arena en typescript (si el lenguaje que compila a javascript creado por micro$oft) en corewar.io y es software libre el repo en github.
Y ya de paso…vengo ha hablar de mi libro, hace unos años estuve limpiando el código fuente de pmars, pero hace mucho que no le doy caña.
Gracias por el aporte MD :) , el link para jugar con corewar.io me dice que esta roto, he añadido al articulo tu repo con el código mas limpio de pmars, gracias tio ;) ¿te apuntas al torneo? si es que lo llegamos a montar algun dia … :P
Puff estoy sin vida, tengo abandonado casi todo, sobre todo las cosas que necesitan de mi presencia física (aunque sea online) como hacklabs o podcast…que tristeza de vida. No obstante gracias.
Cierto, dentro de la página de corewar.io esta roto el link de jugar….jajajaja.
Si no os da mucho asco el tema de npm y tal, se puede levantar una web en local con el proyecto bastante fácilmente (hay un sudo npm install que no me gusta):
$ git clone https://github.com/corewar/corewar.io.git
$ cd corewar.io
$ sudo npm install --global lerna eslint-cli
$ npm run bootstrap
Y te abre una ventana en el navegador por defecto en la url: http://localhost:3000/ con la «app web» del corewar.io .
NO consigo…Cuando ejecuto «make» en la carpeta src indica:
-In file included from sim.c:29:0:
sim.h:92:12: warning:built-in function ‘round’ declaraded as non-function
extern int round;
-In file included from sim.c:29:0:
xmindisp.c:39:10: fatal error: X11/Xlib.h: No existe el archivo o directorio
include <X11/Xlib.h>
Te falta libx11-dev , no obstante echale un vistazo a el fork de MD que esta mucho mas limpio de dependencias y es el mismo programa.
Saludos
Para instalar en Fedora31
sudo dnf install pmars