La segunda parte del proyecto puede ser consultada en este link
David Martínez B34019
Alexander Marín B23892
La cortadora láser del Arcoslab permite realizar cortes sobre plástico y madera, pero para su uso es necesario tener Windows Xp/Vista/7. Entendiendo el protocolo de comunicación es posible implementar las funciones principales del manejo de la cortadora en una aplicación en Debian, lo cual se plantea realizar en este proyecto.
Actualmente para hacer uso de la cortadora láser con el sistema Debian es necesario tener una máquina virtual de Windows Xp/Vista/7 para poder usar la aplicación que controla la cortadora láser, con el desarrollo de la aplicación propuesta sería posible el uso de la cortadora sin la necesidad de utilizar software privativo como Windows Xp/Vista/7 o el mismo programa de la cortadora.
Para realizar la ingeniería reversa del protocolo, se utilizará Wireshark, para así analizar los paquetes que envía la aplicacion de la cortadora a través de la red, la aplicación estará corriendo en una máquina virtual de Windows Xp teniendo como anfitrión a Debian.
Con los comandos básicos obtenidos del análisis de paquetes, se procederá a diseñar la aplicación, esto en lo que corresponde a la primera parte del proyecto. En la segunda parte se procederá a implementarla.
La Full Spectrum Laser es una cortadora laser capaz de cortar multiples materiales en modo vectorizado y rasterizado, sin embargo su utilización se ve afectada al no poseer ninguna especie de soporte por parte de los creadores para su uso en Linux, lo que limita al usuario a utilizar sistimas operativo no gratiutios y por sobre todo restrictivos.
Para el desarrollo de la aplicacion se utilizará la version Sid de debia, cuyo procedimiento se puede encontrar en el siguiente link Instalación de Debian
Por defecto, la instalación realizada en el punto anterior no incluye los drivers necesarios para utilizar el wifi de la computadora(Necesario para la conexion a internet de esta), para realizar esto, es necesario saber que chipset de red inalambrica(wlan) posee nuestra computadora, si no se sabe de antemano, este se puede obtener utilizando:
lspci | less
en la terminal del sistema y buscamos donde dice: Network Controller
Y seguidamente caso anotaremos la identificación de el chipset, en este caso es RTL8188CE
basta con realizar una busqueda simple en los repositorios de Debian para encontrar los controladores necesarios para el chipset, para ello correremos:
sudo apt-get update apt-cache search RTL8188CE
el cual nos retornará un paquete que en este caso se llama firmware-realtek, basta con instalarlo corriendo:
sudo apt-get install firmware-realtek
Es necesario reiniciar la computadora tras este paso (o almenos reloguearse).
Para administrar las conexiones recomiendo utilizar Wicd, que viene instalado por defecto en xfce, sin embargo siempre se puede obtener de los repositorios utilizando
sudo apt-get install wicd
Para instalar una maquina virtual de Windows XP/Vista/7 para poder utilizar la cortadora laser (y capturar los paquetes que esta máquina le envía a la cortadora) se necesitará instalar VirtualBox, este programa se puede instalar directamente desde los repositorios de Debian.
sudo apt-get update sudo apt-get install virtualbox
Tras instalarlo, es necesario poseer un iso de el sistema operativo a escoger, en nuestro caso se utilizo Windows XP. para configurarlo siga los siguientes pasos:
Ejecute en consola:
virtualBox
Damos click en New, nos aparecera una ventana como la siguiente:
en la cual seleccionaremos Microsoft Windows en
Type
y nuestra versión que hayamos escogido, le damos click en next y obtendremos una ventana como la siguiente:
Queda a criterio de cada quien utilizar la memoria RAM que crea necesaria para sustentar la maquina virtual y el programa Retina. para este caso se utilizó 500M.
Seguidamente le damos continuar y marcamos la opción Create a virtual hard drive now
y presionamos el boton Create, aparecerá una ventana pidiendo el tipo de disco duro, seleccionamos la opcion VDI
y le damos Next. En la siguiente ventana le damos Dynamically Allocated
y seleccionamos la cantidad de disco que le queremos asignar a la maquina(Igualmente a criterio del usuario).
Tras realizar estos pasos solo se debe realizar una instalación regular de Windows.
Una vez instalado Windows se debe hacer click derecho en el icono de las 2 computadoras(en VirtualBox) para desplegar un menú, y ahí darle la opción Network Settings
se desplegará una ventana en la cual se debe modificiar la pestaña Attached to
a NAT
tal y como se muestra en la siguiente imagen:
Para este punto nuestra máquina virtual esta configurada y lista para accesar funciones de internet, asi como ser analizada por wireshark (mas adelante)
Una vez realizado lo anterior se debe instalar el software de Retina Engrave cuya instalación es completamente sencilla.
Wireshark es una aplicación indispensable para cumplir nuestros objetivos, ya que esta aplicacion es la encargada de capturar los paquetes en la comunicacion entre la maquina virtual y la cortadora laser. Para comenzar instalaremos el paquete wireshark desde los repositorios de Debian, para esto correremos:
sudo apt-get update sudo apt-get install wireshark
Tras instalar, la aplicacion solo podra capturar paquetes si a esta se le otorga acceso como root, lo cual es muy arriesgado, para arreglar esto correremos:
sudo dpkg-reconfigure wireshark-common
Lo cual nos deberia de mostrar una pantalla como la siguiente:
Le daremos yes
, esto creara un grupo llamado wireshark, en el cual, los usuarios pertencientes a el podrán accesar la captura de paquetes sin necesidad de correr la aplicacion como “root” o “superuser”.
Para agregar un usuario al grupo wireshark es necesario utilizar:
sudo adduser [Tu usuario] wireshark
Al reiniciar o reloguear tu usuario será capaz de utilizar wireshark.
Ghex es un editor Hexadecimal que es especialmente util para el análisis de los paquetes de Wireshark, este muestra los datos de muchas maneras, entre ellas: Cifras enteras, enteros con signo, punto flotante, etc. Tambien tiene la fuencion para observar los paquetes en sentido inverso, es decir, tomar el ultimo bit como el primero, y analizarlo hacia la izquierda. Su instalación es relativamente simple, nada mas hace falta escribir:
sudo apt-get update sudo apt-get install ghex
en la consola para obtenerlo.
Para encender la cortadora primero hay que encender la bomba de agua
la cual basta con conectarla, casi inmediatamente hay que alzar el lado izquierdo de la cortadora de manera que salgan muchas de las burbujas en el el tubo que rodea el láser, ya que estas de no ser sacadas irán dañando el láser. Luego se conecta el ventilador y se enciende, y se verifica que este funcionando
ahora ya se puede girar el gran y llamativo botón rojo para encender la cortadora, la cual desplegará el ip asignado a ésta, necesario para conectarse con RetinaEngrave(RE).
Ahora cuando se van a realizar cortes es imperativo usar el compresor con una presión de 30 psi
ya que en especial materiales como la madera y acrílico arden en llamas cuando se cortan sin el compresor de aire, por lo que además también es imperativo tener un extinguidor de CO2.
Ahora bien con la máquina encendida, RE corriendo en la máquina virtual, Wireshark capturando paquetes podemos empezar con una captura de una acción simple por ejemplo conectarse con la cortadora en RE. Ya con nuestra primer captura podemos inspeccionarlos, lo cual quizás resulte un poco agobiante por lo que sería bueno revisar que es la cabecera tcp/ip, aunque nos podemos dar una idea de que son estas cabeceras solamente “jugando” en la sección de los detalles del paquete y los bytes del paquete, buena idea también sería revisar en que consisten las etiquetas PSH, ACK, SYN de la cabecer tcp y de paso en que consiste 3-way handshake. Seguidamente, en Wireshark filtramos los paquetes mostrados por dirección de ip, con el siguiente texto en el espacio de filtro, de esta manera lograremos vizualizar solamente los paquetes transmitidos desde y hacia ese ip, asumiendo que esa es la dirección de nuestra cortadora.
ip.addr==192.168.17.156
podemos filtar aun mas los resultados de acuerdo al puerto tcp con lo siguiente
tcp.port==12345
de manera que solamente vamos a observar la conversación con este puerto. Sin embargo al menos en este caso la cortadora y RE se comunican a tráves de tres puertos distintos de manera que si comenzamos nuestro análisis de paquetes con ese filtro no veremos las otras conversaciones. Entonces podemos filtrar los paquetes por ip y resaltar con colores distintos las distintas conversaciones y así ver las conversaciones sin pasar a ninguna por desapercibida, para esto basta ir a View→Colorize Conversation. Habiendo consultado los links dados, aplicado el filtro por ip y resaltado las conversaciones con distintos colores nos resultará en un escenario menos confuso. También debemos considerar las opciones de exportar paquetes o mostrar paquetes en una nueva ventana para facilitar la vizualización de estos para así hallar patrones, lo mismo que las opciones de copiar paquetes en el formato hexdump (Offset Hex) que podemos pegar en un documento de texto para ver varios paquetes simultáneamente.
En diversas capturas de paquetes cuando la cortadora se esta conectando y desconectando distinguimos una serie de pasos siempre presentes, los cuales se presentan a continuación. Lo primero que hace RE es hacer un ping a la dirección ip almacenada en el espacio de specify ip, si es que la hay, para determinar si la cortadora esta encendida, aunque este paso no es mandatorio para realizar la conexión. Después RE realiza un 3-way handshake, con el puerto 12345 de la cortadora, de ahora en adelante haremos referencia al puerto 12345 como italk, ya que así es como es identificado en Wireshark, y supondremos un puerto arbitrario conectado a éste con el número 59000, solo para hacer enfasís en que es una conversación entre estos dos puertos y denotaremos el hecho de que italk envía a 59000 como
italk→59000
Después del connect() esto es lo que responde la cortadora
100 Hello 192.168.17.1. FSL Laser Ready, your session ID 00000001\n
y el session ID ira subiendo conforme se vuelva a reconectar
100 Hello 192.168.17.1. FSL Laser Ready, your session ID 00000002\n
Se crea otro socket, distinto del conectado al puerto 12345, el cual se conecta al puerto 12346, con el cual la cortadora envía información sobre el estado actual de la cortadora, del cual hablaremos posteriormente.
59000→italk
pass 180\n
italk→59000
101 GO AHEAD\r\n
Se envía a italk otro paquete cuya interpretación en hexadecimal se muestra a continuación, es decir lo que se origina de agrupar los bits en grupos de 8 y convertir estos grupos a hexadecimal, recomendamos consulta consultar que es Hex dump.
0000 aa 01 14 00 05 00 00 00 00 00 00 00 00 00 00 00 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc 0020 aa 00 88 00 00 00 00 00 43 d3 04 00 87 a6 09 00 0030 2e c9 02 00 20 03 00 00 20 03 00 00 00 08 00 00 0040 ed d2 06 00 db a5 0d 00 40 42 0f 00 e8 03 00 00 0050 e8 03 00 00 e8 03 00 00 43 d3 04 00 87 a6 09 00 0060 2e c9 02 00 10 00 00 00 10 00 00 00 00 08 00 00 0070 00 00 00 00 00 00 00 00 00 00 00 00 02 00 00 00 0080 02 00 00 00 01 00 00 00 00 00 01 b4 01 01 00 00 0090 00 00 00 00 fa 00 00 00 f4 01 00 00 f4 01 00 00 00a0 20 4e 00 00 e0 2e 00 00 30 75 00 00 bb cc bb cc 00b0 bb cc bb cc
En la línea 0070 hay unas pequeñas variaciones cuando se realiza la función Run Job Perimeter con antelación a un intento nuevo de conexión pero el paquete anterior es exactamente igual cuando se conecta por primera vez después de encender la cortadora.
italk→59000
102 OK\r\n
59000→italk
GET DATA0
italk→59000
0x2f85239f\r\n
italk→59000
102 OK\r\n
italk→59000
GET DATA1
italk→59000
0xdb88239f\r\n
italk→59000
102 OK\r\n
hasta aquí termina el inicio de la conexión después de esto si no se le envía ninguna orden, la máquina seguirá enviando paquetes desde el otro puerto, 12346. Para cerrar la conexión simplemente se envía al puerto 12345, lo siguiente
bye\n
italk→59000
105 BYE\r\n
y luego la cortadora cierra los dos sockets, el 12345 y 12346. Vale aclarar que siempre se usan los puertos 12345 y 12346, es decir no varían entre apagado y apagado de la cortadora.
Entre las opciones de RE está la de mover el láser en el eje x y y, lo cual también se puede hacer con los botones embebidos en la cortadora, cuando usamos los botones de RE observamos la presencia de una secuencia de paquetes, a partir de varias repeticiones, moviendo el láser en todas las direcciones y con distinta duración de pasos, encontramos el siguiente patrón:
59000→italk
pass 32\n
italk→59000
101 GO AHEAD\r\n
59000→italk
0000 aa 01 14 00 0c 00 00 00 00 00 00 00 00 00 00 00 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc
este es independiente de la magnitud o dirección del Jog. italk→59000
101 GO AHEAD\r\n
59000→italk
0000 aa 01 14 00 03 02 00 00 00 00 00 00 00 00 00 00 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc
Pero este paquete no es idéntico para distintas direcciones, variando la dirección, es decir probando con Jog Right, Jog Left, Jog Up y Jog Down, observamos que únicamente cambia el sexto byte, siendo 01 para Jog Right, 02 para Jog Left, 03 para Jog Up y 04 para Jog Down.
italk→59000
102 OK\r\n
Probando con pasos largos notamos que despues del paso anterior, la comunicación con italk se reanudaba mucho después, digo la comunicación con el puerto italk, ya que el puerto 12346 sigue enviando paquetes durante este tiempo. La comunicación se reanuda cuando 59000 envía lo siguiente
pass 16\n
por lo que cabe pensar que es con este paquete que se detiene el movimiento del láser, o al menos es el inicio de la secuencia para detenerlo, lo cual sucede en el momento en que se suelta el botón de Jog.
italk→59000
101 GO AHEAD\r\n
59000→italk
0000 aa 06 04 00 73 f7 01 00 bb cc bb cc bb cc bb cc
el cual no varía con respecto a la magnitud del Jog y la dirección de éste
italk→59000
102 OK\r\n
En éste momento ya podemos tener por seguro que el láser se ha detenido.
Para verificar el perímetro del corte a realizar detectamos la siguiente secuencia:
59000→italk
pass 32\n
italk→59000
101 GO AHEAD\r\n
59000→italk
0000 aa 01 14 00 06 00 ff 00 01 00 00 00 c8 00 00 00 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc
Este paquete no siempre es igual pero es muy semejante y sino igual a los que siguen.
italk→59000
102 OK\r\n
Esto se repite cuatro veces, donde únicamente cambia el paquete mostrado en hexadecimal y gracias a que RE tiende a correr muy lento en la máquina virtual, pudimos distinguir que cada una de estas secuencias es para hacer los cuatro movimientos individuales que hace cuando se corre el perímetro, de esta manera el paquete le indica al láser hacia donde y cuanto moverse. Donde los bytes del 13 al 16 dan el movimiento en x y los bytes del 17 al 20 dan el movimiento en y, cuando el láser se mueve hacia arriba o hacia la derecha los ultimos dos bytes son cero y cuando se mueve hacia la izquierda o abajo los ultimos dos byte son ff ff. Y en cuanto a magnitud estos bytes se interpretan de la siguiente manera, tomando como ejemplo el siguiente paquete
0000 aa 01 14 00 06 00 ff 00 01 00 00 00 a0 0f 00 00 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc
en este caso se tiene a0 0f, si se rescribe como 0f a0 y lo vizulizamos como un solo numero hexadecimal fa0 y lo convertimos a base 10 nos quedará 4000, el cual corresponde a un movimiento de 4 in hacia la derecha, vemos que se cumple la relación
distancia recorrida=4000/100
Esta relación se observó para todos los paquetes sin embargo para movimientos hacia la izquierda o abajo se sigue procedimiento similar pero con un paso extra el cual podemos ilustrar partiendo del siguiente paquete:
0000 aa 01 14 00 06 00 ff 00 01 00 00 00 38 ff ff ff 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc
se toma igualmente 38 ff, donde ff38 es 65336, nos sorprendió bastante este resultado ya que era imposible que el láser se hubiera movido 65 pulgadas, sin embargo contemplando este resultado observamos que en realidad esta muy cerca del equivalente en base 10 de los siguientes dos bytes ff ff, que es 65535, así la diferencia es 65535-65336=199, siendo el movimiento de 0.2 in la izquierda, de donde vimos que igualmente tiende a cumplirse la relación
distancia recorridad=199/100=0.199≈2.
Cabe resaltar la semejanza de como indicar el desplazamiento con la resta de vectores, ya que igualmente podemos aplicar el procedimiento para determinar la distancia hacia abajo o a la izquierda, al movimiento hacia la derecha o arriba pero en lugar de la diferencia con ff ff se hace con respecto a 00 00 los siguientes dos bytes en este caso.
Esta es la función para probar el láser, con el cual se activa el láser utilizado para cortar durante un corto intervalo de tiempo, 5 ms es el tiempo por defecto, cabe mencionar que para hacer uso de está función es mandatorio utilizar el compresor de aire, dado que es la función de cortar aplicada sobre un punto, aunque la potencia de éste sea baja. Después de varias capturas de paquetes cuando activabámos la función mencionada encontramos el siguiente patrón:
59000→italk
pass 32\n
italk→59000
101 GO AHEAD\r\n
59000→italk
0000 aa 01 14 00 0d 00 32 00 00 00 00 00 00 00 00 00 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc
Variando el tiempo encontramos que el sétimo byte determina el tiempo, y encontramos que conviertiendo este número hexadecimal a base 10 es diez veces la cantidad de milisegundos que dura la prueba, en este caso 3216 en base 10 es 50 y el paquete mostrado corresponde a la prueba de 5 ms y el siguiente byte se utiliza para valores mayores con 5e 01 para 35 ms y 26 02 para 55 ms, 015e16=350 y 22616=550, donde se sigue la misma relación
cantidad de milisegundos=(equivalente en base 10)/10
Cabe resaltar que la cantidad de tiempo se representa de la misma manera que la cantidad de distancia recorrida en los paquetes de Run Job Perimeter, presentados en la sección anterior. Probando con distintas potencias del vectorizado encontramos que este parámetro no da la potencia del láser, como habiámos asumido previamente, ya que no existe variación de los paquetes para distintas potencias
Teniendo el diseño a cortar en modo vectorizado los siguientes paquetes son los que se envían a la hora de oprimir Run Job en RE.
59000→italk
xjob\n
italk→59000
103 JOB_OK, JobID 00000001 SessionID 00000001\r\n
JobID aumenta con cada vez que se da Run Job.
59000→italk
immediate <cantidad de bytes>\n
italk→59000
102 OK\r\n
59000→italk
data\n
italk→59000
103 JOB_OK, JobID 00000001 SessionID 00000001\r\n
En este punto se conecta otro socket al puerto 12346, digamos que se conecta a 48000.
59000→italk
sending\n
italk→59000
101 GO AHEAD\r\n
Ahora el puerto 12346 envía un gran paquete en varios fragmentos, los cuales son la descripción del corte a realizar. Hecho esto se cierra la conexión con 48000.
italk→59000
104 GOT <candtidad de bytes> bytes\r\n
59000→italk
run\n
italk→59000
102 OK\r\n
Cabe decir que hasta aquí la secuencia para realizar un rasterizado es igual a la de realizar un corte vectorial, a excepción de los datos contenidos en los paquetes enviados al puerto 12346. Los siguientes tres paquetes que se envían a italk son propios del modo vectorial.
59000→italk
pass 32\n
italk→59000
101 GO AHEAD\r\n
59000→italk
0000 aa 01 14 00 16 b4 00 00 00 00 00 00 00 00 00 00 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc
italk→59000
102 OK\r\n
Cuando finaliza el corte se envía a italk
abort\n
italk→59000
102 OK\r\n
El proceso de corte o rasterizado, puede ser pausado simplemente enviando a italk
pause\n
a lo que italk responde
102 OK\r\n
y para continuar basta con
resume\n
a lo que italk responde
102 OK\r\n
y para abortar el trabajo se sigue la siguiente secuencia, tanto para el modo vectorizado como el raster
59000→italk
pass 16\n
italk→59000
101 GO AHEAD\r\n
59000→italk
0000 aa 06 04 00 73 f7 01 00 bb cc bb cc bb cc bb cc
italk→59000
102 OK\r\n
59000→italk
abort\n
italk→59000
102 OK\r\n
Con respecto a los datos sobre el trabajo en raster o corte vectorial, se mandan tres o más paquetes, en ambos modos, dependiendo de la complejidad del trabajo, el primero se muestra a continuación:
0000 02 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0010 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0020 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0040 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0050 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0060 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0070 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0080 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0090 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00a0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00b0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00c0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00d0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00e0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00f0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0100 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0110 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0120 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0130 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0140 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0150 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0160 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0170 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0180 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0190 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01a0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01b0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01c0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01d0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01e0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01f0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0200 05 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0210 00 00 00 00 00 00 00 00
lo cual es bastante llamativo ya que no pareciera contener información significativa, sin embargo creemos que puede ser para una opción que hasta el momento no hemos utlizado, como por ejemplo el cortar varias figuras de una sola vez, pero si se aprecia una diferencia entre el raster y modo vectorial, cuando son datos para un corte vectorial el primer byte es 02 como en este caso, mientras que para modo raster empieza con 03. El segundo paquete podemos ver que tiene muchos bytes 00 en el medio de otros bytes diferentes de cero arriba y abajo, en cuanto a los de arriba, los bytes que ocupan el lugar 13 y 14 en la fila 0040 dan la distancia máxima en x de la figura, es decir lo mismo que se verifica con el Run Job Perimeter, mientras que el primer y segundo byte de la fila 0050 dan la distancia máxima en y, hay que tener presente que estas magnitudes están dadas en el formato particular descrito anteriormente, es decir primero invertimos el orden de los bytes(01cc y 00dc) y encontramos su equivalente en base 10 (460 y 220, lo cual se interpreta como 0.46 in y 0.22 in), estas dos cantidades se aplican por igual al modo raster y vectorial. También notamos que el cuarto byte de la fila 0060 varía solamente en el modo raster y cambia con respecto a la potencia siendo b4 para el 100% o 03 para el 2% como en este caso, el valor del byte, es decir el valor hexadecimal asociado, se puede determinar con la siguiente ecuación:
potencia en base 10=porcentaje de potencia requerido*180/100
y este valor en base 10 se convierte a hexadecimal. En el caso del corte vectorial este valor siempre es b4.
0000 43 d3 04 00 87 a6 09 00 2e c9 02 00 20 03 00 00 0010 20 03 00 00 00 08 00 00 ed d2 06 00 db a5 0d 00 0020 40 42 0f 00 e8 03 00 00 e8 03 00 00 e8 03 00 00 0030 43 d3 04 00 87 a6 09 00 2e c9 02 00 10 00 00 00 0040 10 00 00 00 00 08 00 00 00 00 00 00 cc 01 00 00 0050 dc 00 00 00 02 00 00 00 02 00 00 00 01 00 00 00 0060 00 00 01 03 01 01 00 00 00 00 00 00 fa 00 00 00 0070 f4 01 00 00 f4 01 00 00 20 4e 00 00 e0 2e 00 00 0080 30 75 00 00 17 00 00 00 00 00 00 00 00 00 00 00 0090 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00a0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00b0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00c0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00d0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00e0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00f0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0100 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0110 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0120 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0130 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0140 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0150 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0160 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0170 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0180 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 0190 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01a0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01b0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01c0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01d0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01e0 00 00 00 00 00 00 00 00 01 00 00 00 c8 02 00 00 01f0 ad db c5 92 95 57 18 86 d1 73 68 34 b8 bb bb bb 0200 bb bb 6b 82 04 77 77 4b 70 b7 c6 dd 9d 04 87 10 0210 bc 71 77 97 6b 80 be 83
Con respecto al los últimos bytes, ya determinamos que los bytes número 13 y 14, si realizamos la misma conversión de antes, nos da la cantidad de bytes de las últimas tres filas y los que son enviados en el tercer paquete y hasta cuarto, en caso de ser muchos bytes, sin tomar en cuenta las cabeceras, en este caso tenemos que 02c816=712 bytes. De modo que ya hemos reducido aun más donde creemos que se pasan los datos que le ordenan a los motores como moverse y cuanta potencia del láser usar. Después de varias capturas hemos notado varios fenómenos a tomar en cuenta, a mayor velocidad menor cantidad de bytes, a mayor distancia aumenta la cantidad de bytes, pero esto no sucede de una manera lineal e incluso para aumentos muy pequeños hasta puede disminuir en un byte lo cual suponemos que puede deberse a cambios en la cantidad de cifras significativas de los datos que presumimos como cantidades númericas, al aumentar la potencia, aumenta la cantidad de bytes. Dado esto hemos hecho capturas de manera de obtener la menor cantidad posible de bytes y partir de ahí variar los parámetros, sin embargo se ha de tener presente no variarlos con incrementos o decrementos excesivamente pequeños ya que en estos casos RE lo redondea, dando origen cortes iguales, además es posible que la cortadora ni siquiera puede trabajar a esos niveles de presición. Pero tampoco se deben hacer cambios demasiado grandes ya que los datos cambian sustancialmente y se hace muy díficil encontrar un patrón, a menos que se quiera comprobar algo en especial, por el momento hemos empezado a reconocer similitudes y hasta cadenas de bytes idéticas de esta manera, sin embargo no hemos llegado a nada concluyente en cuanto a como se le dan las órdenes al láser y los motores. Estas experiencias las tomaremos en cuenta a la hora de continuar con la ingeniería reversa del protocolo.
El puerto 12346 manda una gran cantidad de paquetes sobre la cortadora y lo que hace, se puede optar pero tambien se podría utilizar para evitar que el láser se mueva indefinidamente hasta uno de los bordes lo que dañaría los motores y las bandas, o para saber que esta haciendo el laser en ese momento, ya que puede ser que si se manda una orden de mover los motores mientras estos están bloqueados con el botón embebido en la cortadora estos resulten dañados, lo cual se podría evitar si se sabe que esta haciendo la cortadora, lo cual lo podemos saber gracias a los paquetes mencionados. A continuación se muestra uno de dichos paquetes en su interpretación hexadecimal:
0000 ce 5a ae 72 01 00 02 00 00 00 00 00 00 00 00 00 0010 f7 4f 00 00 00 00 00 00 1a 6b 4c 68 00 00 00 00 0020 30 ff ff ff 00 00 00 00 00 00 00 00 00 00 00 00 0030 00 00 00 00 93 b7 22 2c 17 01 00 00 9b af cb 2b 0040 df 00 a8 0b
Después de varias pruebas, moviendo el láser con el Jog tanto de RE como el que esta en la cortadora, encontramos que el primer y segundo byte de la linea 0020, es la posición relativa en y y el décimocuarto y décimotercer byte de la fila 0010 dan la posición relativa en x, digo relativa porque si estos se mueven manualmente con la mano desbloqueando el láser, estos paquetes no hacen una distinción, solamente dicen que tanto se ha movido desde la posición de inicio el láser, lo interesante es que está dado por dos dígitos el digito más significativo es el que está más a la derecha, esto para ambas cordenadas, donde siguen exactamente el mismo formato para representar distancias en los paquetes de Run Job Perimeter. Algo parecido sucede con los dos bytes antes de los que dan la cordenada x, ya que el de la izquierda va aumentando lentamente con el tiempo mientras que el byte a su derecha aumenta rápidamente, por lo que podemos decir que estos dos dan el tiempo, es posible que los dos bytes que están antes de los que dan el tiempo sean los dígitos menos significativos del mismo tiempo pero no se puede decir con certeza. Entonces sería bueno tener presente esta forma de representar magnitudes en el resto de los análisis de paquetes.
Lo que esta haciendo la cortadora viene dado por el quinto byte, en la siguiente tabla se presentan los valores que toma éste y la respectiva acción o estado: En la siguiente tabla
byte | |
---|---|
corte vectorial | 01 |
rasterizado | 02 |
jog | 03 |
yendo a home | 04 |
run job perimeter | 06 |
unlock(de la cortadora) | 07 |
Antes de enviar datos a la cortadora para hacer pruebas como el test fire o Go to home, siempre es bueno hacer pruebas con sockets en nuestra misma computadora a la vez que capturamos los paquetes, lo primero sera escoger el la interfaz “lo” para poder capturar los datos que vamos a enviar en nuestro propio host entre dos sockets distintos. Ahora creamos dos sockets para trasmitir datos entre ellos uno que actúe como cliente y el otro como servidor, lo cual es se puede consultar aquí. A diferencia de algunos tutoriales para efectos de realizar pruebas e implementar la aplicación en vez de usar send() para enviar datos usaremos sendall() para complicarnos menos. Ya que con send() puede que no se envíen todos los bytes y retorna la cantidad de bytes enviados por lo que habría que adicionar mas código para verificar que todos los datos sean enviados, mientras que con sendall() no, con esta función nos aseguramos de enviar todo a menos que ocurra un error en dado caso se levanta una excepción. Ya con esto se puede empezar empezar a mandar datos de un socket al otro y vizualizar estos en wireshark. Con esto nos daremos cuenta que uno de los varios pasos para conectarse es simplemente mandar “pass 180\n”. Es importante decir que no se deben enviar paquetes al azar para ver que pasa, a modo de ejemplo esta el comando de hacer que se mueva el láser ya que con este se envía un paquete y no es sino hasta que se manda otro paquete que el laser termina de moverse de este modo si no enviamos este otro paquete el láser seguirá moviendose hasta el borde lo que dañará los motores, además podríamos dejar inservible la cortadora. Sin embargo hay paquetes que no son tan cortos como este o que quiza cuando vemos su interpretación en ascii en wireshark, se observan “.” sin embargo esto solo significa que no es uno de los caracteres imprimibles entre 33 y 126. Por tanto si se quiere enviar una cadena de 8 bits cuya interpretación en hexadecimal es “ae”, no enviamos “ae” sino como “\xae”. Sin embargo si deseamos enviar un paquete, que siempre es igual, a la cortadora como el siguiente
0000 aa 01 14 00 06 00 ff 00 01 00 00 00 00 00 00 00 0010 00 00 00 00 00 00 00 00 bb cc bb cc bb cc bb cc
tendríamos que quitar el offset y cambiar los espacios en blanco por \x, una mejor alteranativa es usar unhexlify() del modulo binascii en python.
de esta manera copiamos los datos como hexstream
y enviamos con los siguientes comandos desde alguno de nuestros sockets con los que estamos experimentando
#almacenamos los datos en una variable hexStream=”aa0114000600ff0001000000000000000000000000000000bbccbbccbbccbbcc” #importamos el modulo binascii para hacer uso de unhexlify import binascii #usamos unhexlify para conseguir que sea de la forma \xaa\x01\x14 … datosAenviar=binascii.unhexlify(hexStream) #solo resta enviar los datos al otro socket que creamos en la otra consola de ipython cliente.sendall(datosAenviar)
Ahora podemos revisar en Wireshark que hemos enviado al otro socket un paquete que coincide con el que RE le envía a la cortadora.