convertir una cadena hexadecimal a binario y enviar con netcat

46

Tengo un archivo binario que puedo enviar con netcat:

$ nc -l localhost 8181 < my.dat

El archivo contiene esto:

$ xxd my.dat
0000000: 0006 3030 3030 4e43                      ..0000NC

Lo que realmente quiero hacer es enviar la cadena hexadecimal directamente. He intentado esto:

$ echo '0006303030304e43' | nc -l localhost 8181

Sin embargo, el comando anterior solo envía la cadena ascii directamente a nc.

Chris Snow
fuente

Respuestas:

55

He utilizado el -r y -p interruptor para xxd :

$ echo '0006303030304e43' | xxd -r -p | nc -l localhost 8181

Gracias a la inspiración de la respuesta de @Gilles, aquí hay una versión en perl:

$ echo '0006303030304e43' | perl -e 'print pack "H*", <STDIN>' | nc -l localhost 8181
Chris Snow
fuente
Funciona muy bien para el formato bytea hexadecimal de Postgres una vez que se separa el \ x principal.
nathancahill
¡Gracias! ¡Funciona muy bien también para verificar los resúmenes de diccionarios de Firefox en manifiesto! md5sum ../it/manifest.json | awk '{print $1}' | xxd -r -p | hd
Avio
26

Aquí una solución sin xxdo perl:

Si la echoconstrucción de su shell lo admite ( bashy lo zshhace, pero no dash), solo necesita usar los escapes de barra invertida correctos:

echo -ne '\x00\x06\x30\x30\x30\x30\x4e\x43' | nc -l localhost 8181

Si usted tiene /bin/echode GNU coreutils (casi estándar en los sistemas Linux) o de busybox que se puede utilizar, también.

Con sedusted puede generar un patrón escapado:

$ echo '0006303030304e43' | sed -e 's/../\\x&/g'
\x00\x06\x30\x30\x30\x30\x4e\x43

Conjunto:

echo -ne "$(echo '0006303030304e43' | sed -e 's/../\\x&/g')" | nc -l localhost 8181
jofel
fuente
Muy buena solución!
Chris Snow
2
Reemplazar echocon printfelimina las conjeturas si echo admite características extendidas o no. printf "$(echo '0006303030304e43' | sed -e 's/../\\x&/g')" | nc -l localhost 8181.
Jaakko
12

Si es así xxd, es fácil: puede convertir ay desde hexadecimal.

echo '0006303030304e43' | xxd -r -p | nc -l localhost 8181

No creo que haya una forma razonable (y razonablemente rápida) de convertir hexadecimal a binario usando solo herramientas POSIX. Se puede hacer bastante fácil en Perl. El siguiente script convierte hexadecimal a binario, ignorando cualquier carácter de entrada que no sea un dígito hexadecimal. Se queja si una línea de entrada contiene un número impar de dígitos hexadecimales.

#!/usr/bin/env perl
$^W = 1;
$c = undef;
while (<>) {
    tr/0-9A-Fa-f//cd;
    if (defined $c) { warn "Consuming $c"; $_ = $c . $_; $c = undef; }
    if (length($_) & 1) { s/(.)$//; $c = $1; }
    print pack "H*", $_;
}
if (!eof) { die "$!"; }
if (defined $c) { warn "Odd number of hexadecimal digits"; }

Si realmente necesita apegarse a POSIX (por ejemplo, en un dispositivo integrado), le recomiendo usar Base64 en lugar de hexadecimal. Puede usar uudecode para decodificar Base64. La entrada debe tener el formato del encabezado y la línea final producida por uuencode , no puede ser Base64 sin formato .

uudecode <<EOF | nc -l localhost 8181
begin-base64 644 -
AAYwMDAwTkM=
====
EOF
Gilles 'SO- deja de ser malvado'
fuente
1

Similar a esto: https://stackoverflow.com/questions/1604765/linux-shell-scripting-hex-string-to-bytes/47253233#47253233

Escribí una herramienta que realiza varias transformaciones de stdin y escupe el resultado a stdout. cryptocli ddsolo hará esas transformaciones y nada más.

echo -n 0006303030304e43 | cryptocli dd -decoders hex | nc -l localhost 8081

Trabajará para ti.

La herramienta es de código abierto, puede encontrarla aquí: https://github.com/tehmoon/cryptocli

Editar:

También puede codificar directamente a hexadecimal utilizando mi herramienta:

cat my.dat | cryptocli dd -encoders hex | nc -l localhost 8081
tehmoon
fuente
(1) ¿Qué 616263tiene que ver con esta pregunta? Utilice los datos de la pregunta. (2) ¿Puedes explicar cómo funciona esto? No responda en los comentarios, edite su respuesta para que sea más clara y completa.
G-Man dice 'Restablecer a Monica' el