Servicios y sistemas informáticos para Internet. Curso 2008-2009
Tabla de contenidos
Antes de empezar hay que conectarse a tecgrid03.epv.uniovi.es, la máquina donde se van a realizar las prácticas. La conexión debe ser ssh, por lo que es necesario utilizar un cliente que soporte este protocolo. Se recomienda utilizar el PuTTY.
Antes de poder ejecutar comandos sobre globus tenemos que obtener un proxy.
$>
grid-proxy-init
Your identity: /O=Grid/OU=GlobusTest/OU=simpleCA-tecgrid03.epv.uniovi.es/OU=atc/CN=Rosco
Enter GRID pass phrase for this identity:
Creating proxy ................................ Done
Your proxy is valid until: Fri Feb 6 06:30:23 2009
Vamos a empezar creando una estructura de directorios para almacenar los ficheros que vamos a utilizar en los ejercicios.
$>
cd ~$>
mkdir datagrid$>
mkdir datagrid/gridftp$>
cd datagrid/gridftp
Comprobamos que tenemos la variable de entorno $USER configurada correctamente.
$>
echo $USER
ruf
Establecemos la variable de entorno $HOST para que contenga el nombre de la máquina sobre la que vamos a trabajar.
$>
export HOST=tecgrid01.epv.uniovi.es$>
echo $HOST tecgrid01.epv.uniovi.es
Creamos un directorio en el temporal de $HOST con nuestro nombre de usuario. Para ello tenemos que ejecutar el comando mkdir sobre $HOST.
$>
globus-job-run $HOST /bin/mkdir /tmp/$USER
Podemos comprobar si se ha creado correctamente listando su contenido.
$>
globus-job-run $HOST /bin/ls -al /tmp/$USER
total 28
drwxrwxr-x 2 ruf ruf 4096 Feb 5 18:28 .
drwxrwxrwt 14 root root 20480 Feb 5 18:35 ..
Ahora vamos a crear unos ficheros que utilizaremos en las pruebas.
$>
dd if=/dev/zero of=1mb-$USER bs=10000 count=100 100+0 records in 100+0 records out 1000000 bytes (1.0 MB) copied, 0.00636649 seconds, 157 MB/s$>
dd if=/dev/zero of=10mb-$USER bs=10000 count=1000 1000+0 records in 1000+0 records out 10000000 bytes (10 MB) copied, 0.127192 seconds, 78.6 MB/s$>
dd if=/dev/zero of=100mb-$USER bs=10000 count=10000 10000+0 records in 10000+0 records out 100000000 bytes (100 MB) copied, 0.97683 seconds, 102 MB/s$>
ls -l total 108528 -rw-rw-r-- 1 ruf ruf 100000000 Feb 5 18:53 100mb-ruf -rw-rw-r-- 1 ruf ruf 10000000 Feb 5 18:53 10mb-ruf -rw-rw-r-- 1 ruf ruf 1000000 Feb 5 18:52 1mb-ruf
Transferimos el fichero pequeño con la depuración activada para observar las operaciones que se realizan.
$>
globus-url-copy -dbg file:///$PWD/1mb-$USER gsiftp://$HOST/tmp/$USER/
debug: starting to put gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf
debug: connecting to gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
220 tecgrid01.epv.uniovi.es GridFTP Server 2.7 (gcc32dbg, 1204845443-63) [VDT patched 4.0.7] ready.
debug: authenticating with gsiftp://tecgrid01.epv.uniovi.es;/tmp/ruf/1mb-ruf
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
230 User ruf logged in.
debug: sending command:
SITE HELP
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
214-The following commands are recognized:
ALLO ESTO RNTO APPE DCAU MODE SIZE STRU
TYPE DELE SITE CWD ERET FEAT LIST NLST
MLSD MLST PORT PROT EPRT PWD QUIT REST
STAT SYST MKD RMD CDUP HELP NOOP EPSV
PASV TREV SBUF MDTM CKSM OPTS PASS SPAS
PBSZ SPOR RETR STOR USER RNFR LANG
214 End
debug: sending command:
FEAT
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
211-Extensions supported
UTF8
LANG EN
DCAU
PARALLEL
SIZE
MLST Type*;Size*;Modify*;Perm*;Charset;UNIX.mode*;UNIX.owner*;UNIX.group*;Unique*;UNIX.slink*;
ERET
ESTO
SPAS
SPOR
REST STREAM
MDTM
211 End.
debug: sending command:
TYPE I
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
200 Type set to I.
debug: sending command:
PBSZ 1048576
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
200 PBSZ=1048576
debug: sending command:
PASV
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
227 Entering Passive Mode (192,168,100,200,224,163)
debug: sending command:
ALLO 1000000
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
200 ALLO command successful.
debug: sending command:
STOR /tmp/ruf/1mb-ruf
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
150 Begining transfer.
debug: data callback, no error, buffer 0xb7ee2008, length 1000000, offset=0, eof=true
debug: response from gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/1mb-ruf:
226 Transfer Complete.
debug: operation complete
$? indica el valor de retorno del último comando ejecutado. Si todo ha ido bien imprime el valor 0.
$>
echo $?
0
Comprobamos que el fichero ha llegado a su destino.
$>
globus-job-run $HOST /bin/ls -l /tmp/$USER
total 984
-rw-r--r-- 1 ruf ruf 1000000 Feb 5 19:00 1mb-ruf
También podemos transferir entre dos servidores de GridFTP.
$>
globus-url-copy gsiftp://$HOST/tmp/$USER/1mb-$USER gsiftp://`hostname`/tmp/1mb-$USER-bis$>
globus-url-copy gsiftp://`hostname`/tmp/1mb-$USER-bis gsiftp://$HOST/tmp/$USER/$>
globus-job-run $HOST /bin/ls -l /tmp/$USER total 1968 -rw-r--r-- 1 ruf ruf 1000000 Feb 5 20:01 1mb-ruf -rw-r--r-- 1 ruf ruf 1000000 Feb 5 20:01 1mb-ruf-bis
Ahora transferimos el fichero de remoto a local.
$>
globus-url-copy gsiftp://$HOST/tmp/$USER/1mb-$USER-bis file:///$PWD/1mb-$USER-bis$>
ls -l total 109512 -rw-rw-r-- 1 ruf ruf 100000000 Feb 5 18:53 100mb-ruf -rw-rw-r-- 1 ruf ruf 10000000 Feb 5 18:53 10mb-ruf -rw-rw-r-- 1 ruf ruf 1000000 Feb 5 18:52 1mb-ruf -rw-rw-r-- 1 ruf ruf 1000000 Feb 5 20:02 1mb-ruf-bis
Podemos obtener información sobre la velociad de transferencia.
$>
globus-url-copy -vb file:///$PWD/100mb-$USER gsiftp://$HOST/tmp/$USER/
Source: file:////home/ruf/datagrid/gridftp/
Dest: gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/
100mb-ruf
93323264 bytes 19.30 MB/sec avg 37.00 MB/sec inst
Otra opción que ofrece el GridFTP es la transferencia de ficheros utilizando varios flujos de datos en paralelo. Para probar está opción, primero vamos a borrar los ficheros transferidos.
$>
globus-job-run $HOST /bin/rm -f /tmp/$USER/*
Ahora volvemos a hacer la transferencia con varios flujos de datos (-p significa con dos flujos de datos).
$>
globus-url-copy -p 2 -vb file:///$PWD/100mb-$USER gsiftp://$HOST/tmp/$USER/
Source: file:////home/ruf/datagrid/gridftp/
Dest: gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/
100mb-ruf
100000000 bytes 28.05 MB/sec avg 28.05 MB/sec inst
Dependiendo de las condiciones de la red se pueden obtener mejores tasas de transferencias, como ocurrió en este caso donde se incrementó 10 MB/sec la velocidad de transferencia media.
Volvemos a borrar los ficheros transferidos.
$>
globus-job-run $HOST /bin/rm -f /tmp/$USER/*
El RFT es una capa que se sitúa sobre GridFTP que proporciona fiabilidad y tolerancia a fallos a la transferencia de ficheros.
Para realizar una transferencia fiable es necesario crear un fichero que contenga toda la información necesaria para realizar la transferencia. Básicamente se necesita un fichero equivalente al que se utiliza para describir un trabajo de ejecución, salvo que en este caso se refiere a un trabajo de transferencia.
Como siempre, vamos a empezar creando un directorio.
$>
mkdir ~/datagrid/rft$>
cd ~/datagrid/rft
Creamos el fichero de descripción de transferencia.
$>
cat > transfer.xfr
#true=binary false=ascii true #Block size in bytes 16000 #TCP Buffer size in bytes 16000 #Notpt (No thirdPartyTransfer) false #Number of parallel streams 1 #Data Channel Authentication (DCAU) true # Concurrency of the request 1 #Grid Subject name of the source gridftp server null #Grid Subject name of the destination gridftp server null #Transfer all or none of the transfers false #Maximum number of retries 10 #Source/Dest URL Pairs gsiftp://_HOST_SRC_:2811/proc/cpuinfo gsiftp://_HOST_DST_:2811/tmp/_USER_/info
Reemplazamos _USER_ por nuestro nombre de usuario para que no haya conflictos. Reeplazamos también _HOST_SRC_ y _HOST_DST_. Por último, verificamos que está correcto.
$>
sed -i "s/_USER_/$USER/" transfer.xfr$>
sed -i "s/_HOST_SRC_/`hostname`/" transfer.xfr$>
sed -i "s/_HOST_DST_/$HOST/" transfer.xfr$>
tail -n 2 transfer.xfr gsiftp://tecgrid03.epv.uniovi.es:2811/proc/cpuinfo gsiftp://tecgrid01.epv.uniovi.es:2811/tmp/ruf/info
A continuación, vamos a hacer la transferencia.
$>
rft -h tecgrid03.epv.uniovi.es -r 9443 -f transfer.xfr
Number of transfers in this request: 1
Subscribed for overall status
Termination time to set: 60 minutes
Overall status of transfer:
Finished/Active/Failed/Retrying/Pending
0/1/0/0/0
Overall status of transfer:
Finished/Active/Failed/Retrying/Pending
1/0/0/0/0
All Transfers are completed
Inicialmente la transferencia comienza en estado Pending, continúa a estado Active para finalizar en estado Finished. Dependiendo de la rapidez de la transferencia es posible que no se vea alguno de los estados. También puede ocurrir que la transferencia falle (estado Failed) y tenga que reintentar la transferencia.
Podemos comprobar si la transferencia se ha realizado correctamente.
$>
globus-job-run $HOST /bin/cat /tmp/$USER/info
processor : 0
vendor_id : GenuineIntel
cpu family : 6
model : 15
model name : Intel(R) Core(TM)2 CPU 6600 @ 2.40GHz
...
Una de las posibilidades de RFT es realizar múltiples transferencias. Para ello, al final del fichero de descripción del trabajo de transferencia hay que indicar tantos pares fuente/destino como transferencias se quieran realizar. A modo de ejemplo realiza una transferencia utilizando RFT que transfiera a gsiftp://$HOST/tmp/$USER/ los tres ficheros creados en el ejercicio del GridFTP (recuerda que el RFT sólo permite third party transfer, de gsiftp a gsiftp). Además, tendrás que mover previamente los ficheros de tu carpeta a otra en el temporal /tmp/$USER o el servicio de gridftp no tendrá permiso para acceder a los ficheros.
Después de hacer el ejercicio de transferencia, comprobamos que los ficheros han llegado a su destino.
$>
globus-job-run $HOST /bin/ls -l /tmp/$USER
total 10800
-rw-rw-r-- 1 ruf ruf 100000000 Feb 5 18:53 100mb-ruf
-rw-rw-r-- 1 ruf ruf 10000000 Feb 7 10:46 10mb-ruf
-rw-rw-r-- 1 ruf ruf 1000000 Feb 7 10:46 1mb-ruf
-r--r--r-- 1 ruf ruf 469 Feb 7 10:21 info
Otra de las opciones que tenemos con el RFT es la programación del borrado de ficheros. Por ejemplo, para borrar el fichero info, creamos el siguiente fichero de descripción.
$>
cat > delete.xfr
# Subject name (if null then defaults to host subject) null gsiftp://_HOST_DST_:2811/tmp/_USER_/info
$>
sed -i "s/_USER_/$USER/" delete.xfr$>
sed -i "s/_HOST_DST_/$HOST/" delete.xfr$>
cat delete.xfr # Subject name (if null then defaults to host subject) null gsiftp://tecgrid01.epv.uniovi.es:2811/tmp/ruf/info
Enviamos el trabajo.
$>
rft-delete -h tecgrid03.epv.uniovi.es -r 9443 -f delete.xfr
creating a rft resource
Subscribed for overall status
Termination time to set: 60 minutes
Overall status of transfer:
Finished/Active/Failed/Retrying/Pending
0/1/0/0/0
Overall status of transfer:
Finished/Active/Failed/Retrying/Pending
1/0/0/0/0
All Transfers are completed
Crea otro fichero de descripción de borrado para el resto de ficheros. Envía el trabajo y comprueba que se han eliminado correctamente.
El servicio de gestión de réplicas permite que nos olvidemos de la localización física de un fichero, servidor y directorio, y trabajar con nombres lógicos. Un nombre lógico puede hacer referencia a un nombre físico o a varios, ya que el fichero puede estar replicado.
Antes de empezar, vamos a crear un nuevo directorio para contener los ficheros.
$>
mkdir ~/datagrid/rls$>
cd ~/datagrid/rls
En primer lugar, vamos a comprobar que el servidor RLS está activo.
$>
globus-rls-admin -p rls://tecgrid03.epv.uniovi.es
ping rls://tecgrid01.epv.uniovi.es: 0 seconds
Vamos a crear un fichero muy simple para trabajar sobre él.
$>
cat > file-$USER.txt
Escribe algo en el fichero.
Ahora vamos a transferirlo.
$>
globus-url-copy file:///$PWD/file-$USER.txt gsiftp://$HOST/tmp/$USER/
A continuación vamos a realizar una petición al servidor de RLS para que establezca un mapeo entre el fichero que acabamos de transferir y un nombre lógico denominado file-$USER (el shell sustituye la variable de entorno $USER).
$>
globus-rls-cli create file-$USER gsiftp://$HOST/tmp/$USER/file-$USER.txt rls://$HOST
El formato de este comando es globus-rls-cli create lfn pfn rls://servidor, donde lfn es el nombre lógico, pfn es el nombre físico, y el último parámetro es la dirección del servidor.
Si preguntamos al servidor por el nombre lógico nos devolverá el nombre físico que acabamos de mapear.
$>
globus-rls-cli query lrc lfn file-$USER rls://$HOST
file-ruf: gsiftp://tecgrid01.epv.uniovi.es.atc/tmp/ruf/file-ruf.txt
En el comando anterior, el parámetro lrc, está indicando que queremos preguntar al catálogo de réplicas locales (Local Replica Catalog), que es el que contiene el mapeo de nombres lógicos a físicos. Esta información se guarda en una base de datos a la que el servidor de RLS accede.
Podemos añadir más mapeos al nombre lógico, de forma que haga referencia a más de un nombre físico.
$>
cp file-$USER.txt /tmp/$USER$>
globus-rls-cli add file-$USER gsiftp://`hostname`/tmp/$USER/file-$USER.txt rls://$HOST
Si volvemos a preguntar al servidor por el nombre lógico nos devolverá los dos nombres físicos.
$>
globus-rls-cli query lrc lfn file-$USER rls://$HOST
file-ruf: gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/file-ruf.txt
file-ruf: gsiftp://tecgrid03.epv.uniovi.es/tmp/ruf/file-ruf.txt
Pregunta a uno de tus compañeros por el nombre lógico que ha utilizado. Busca la ubicación física del fichero y transfiérelo a $HOME/datagrid/rls. Por último, comprueba su contenido.
Un servidor de RLS se puede configurar como LRC (Location Replica Catalog), como RLI (Replica Location Index) o como ambos. Hasta ahora hemos estado trabajando con la parte encargada de gestionar el catálogo de réplicas locales.
El índice de localización de réplicas (RLI), a diferencia del LRC que contiene mapeos entre nombre lógicos y físicos, contiene mapeos entre nombres lógicos y servidores RLS. Este servicio está diseñado para ser una capa de nivel superior al LRC. El funcionamiento es el siguiente, cuando se crea un mapeo entre un nombre lógico y uno físico se almacena la información en el LRC. Además, cada cierto tiempo el servidor RLS que contiene el catálogo de réplicas locales envía información a un servidor que actúe de RLI sobre los nombres lógicos registrados. El RLI almacena los nombres lógicos registrados en ese servidor. Posteriormente, se le pueden hacer consultas al RLI sobre un nombre lógico, y este responderá con el nombre del servidor RLS que contiene el LRC con la información de su ubicación física.
Para preguntar al RLI sobre un nombre lógico se utiliza el comando globus-rls-cli query rli.
$>
globus-rls-cli query rli lfn file-$USER rls://$HOST
file-ruf: rls://tecgrid01.epv.uniovi.es:39281
En el servidor RLS se configura la forma en la que se informa al RLI de los nuevos registros de réplicas. En ocasiones, esta actualización es periódica, con lo que podría darse el caso de que obtengamos información del nombre lógico en el LRC pero no en el RLI. En ese caso, ocurriría lo siguiente.
$>
globus-rls-cli query rli lfn file-$USER rls://$HOST
globus_rls_client: LFN doesn't exist: file-ruf
Partiendo de que un fichero ha sido registrado en el servicio de réplicas con un nombre lógico, la secuencia de operaciones para acceder a ese fichero en un entorno grid sería la siguiente:
Preguntar al servidor que actúa de RLI por el nombre lógico (globus-rls-cli query rli lfn ...). Se obtendrá la lista de servidores RLS que contienen el LRC donde el nombre lógico está mapeado a un nombre físico.
Preguntar a los servidores RLS obtenidos anteriormente por el nombre lógico (globus-rls-cli query lrc lfn ...). Se obtendrá la información sobre la ubicación física del fichero, puede ser una o varias.
Dada una ubicación física, transferir el fichero utilizando globus-url-copy
Esta secuencia de operaciones la podemos traducir en un programa que automatice las operaciones.
$>
cat > getlfn.py
#!/usr/bin/env python import os, string, sys if len(sys.argv) != 3: sys.exit("Usage: getlfn <lfn> <rli_server>") lfn = sys.argv[1] rli_server = sys.argv[2] rli_command_base = "globus-rls-cli query rli lfn %s %s 2>/dev/null" lrc_command_base = "globus-rls-cli query lrc lfn %s %s 2>/dev/null" transfer_command_base = "globus-url-copy %s file:///$PWD/%s 2>/dev/null" #Preguntar por el lfn al rli rli_command = rli_command_base % (lfn, rli_server) rli_query = os.popen(rli_command) rli_query_results = rli_query.readlines() if rli_query.close() != None: sys.exit("RLI query failed") #Preguntar por el lfn a cada lrc for rli_line in rli_query_results: lrc_server = rli_line.split()[1] print "LRC server " + lrc_server + ":" lrc_command = lrc_command_base % (lfn, lrc_server) lrc_query = os.popen(lrc_command) lrc_query_results = lrc_query.readlines() if lrc_query.close() != None: print "LRC query failed on " + lrc_server else: #Intentar transferir desde cada pfn for lrc_line in lrc_query_results: pfn = lrc_line.split()[1] transfer_command = transfer_command_base % (pfn, lfn) transfer = os.popen(transfer_command) if transfer.close() == None: sys.exit(pfn + " -> transfer OK") print pfn + " -> transfer FAIL"
Intenta comprender el funcionamiento de programa anterior, como verás su funcionamiento es bastante sencillo. Su objetivo es transferir al directorio actual el fichero al cual se refiere el nombre lógico que recibe como parámetro.
Para probarlo vamos a darle permisos de ejecución.
$>
chmod +x getlfn.py
Vamos a probarlo con el nombre lógico que creamos en los ejercicios anteriores.
$>
./getlfn.py file-$USER rls://$HOST
LRC server rls://tecgrid01.epv.uniovi.es:39281:
gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/file-ruf.txt -> transfer OK
El programa getlfn transfiere el fichero y lo deja en el directorio actual con el nombre lógico.
$>
cat file-$USER
...
Ahora vamos a ver que pasaría si una de las réplicas no existe.
$>
globus-job-run $HOST /bin/rm /tmp/$USER/file-$USER.txt$>
./getlfn.py file-$USER rls://$HOST LRC server rls://tecgrid01.epv.uniovi.es:39281: gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/file-ruf.txt -> transfer FAIL gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/file-ruf.txt -> transfer OK
Si la transferencia desde una ubicación física falla, se prueba con otra. Una gran ventaja de utilizar el servicio de réplicas es la tolerancia a fallos del sistema.
Los ejemplos que hemos realizado son muy básicos pero permiten ver las posibilidades de las herramientas. Los comandos con los que hemos estado trabajando se utilizan en todo el mundo para transferir petabytes de información y gestionar millones de réplicas.
El objetivo de este ejercicio es ejecutar un trabajo que sea capaz de crackear las contraseñas de los usuarios. Para ello vamos a aplicar un algoritmo de fuerza bruta basado en un diccionario.
Como siempre, vamos a empezar creando un directorio para contener los ficheros de ejercicio.
$>
mkdir ~/datagrid/pcrack$>
cd ~/datagrid/pcrack
A continuación vamos a crear el diccionario, que va a consistir en un fichero con una palabra en cada línea. Escribe las palabras que quieras, pero haz que alguna de ellas sea "0abcdef" (sin comillas).
$>
cat > dict-$USER
Una vez que hayas creado el diccionario, vamos a crear el fichero shadow.
$>
cat > shadow
hasan:$1$/Uesk54D$JDsAQMucfPz45gjYcIgW00:14285:0:99999:7:::
El fichero shadow contiene las contraseñas encriptadas en el formato habitual de los sistemas Unix.
A continuación vamos a crear el programa que se va a encargar de desencriptar las contraseñas utilizando fuerza bruta.
$>
cat > pcrack.py
#!/usr/bin/env python # -*- coding: utf-8 -*- import crypt, string, time, sys, codecs if len(sys.argv) != 3: sys.exit("Usage: crypto <shadow> <dict>") # Leer palabras del diccionario dict_words = [] dict_file = open(sys.argv[2]) for line in dict_file.readlines(): dict_words.append(line.strip()) dict_file.close() # Leer fichero de contraseñas passwords = {} pw_file = open(sys.argv[1]) for line in pw_file.readlines(): pw_fields = string.splitfields(line, ':') if pw_fields[1] != "*" and pw_fields[1] != "!": passwords[pw_fields[0]] = pw_fields[1] pw_file.close() start_time = time.time() # Buscar for word in dict_words: for user, password in passwords.iteritems(): salt = password[:14] if crypt.crypt(word, salt) == password: print user, " = ", word elapsed_sec = time.time() - start_time crypt_calls = len(passwords)*len(dict_words) print crypt_calls,"words in", elapsed_sec, "sec, speed:", crypt_calls/elapsed_sec, "words/sec"
El funcionamiento del programa anterior es bastante claro. Recibe como argumentos el nombre del fichero shadow y el nombre del fichero con el diccionario. Lee el shadow y el diccionario, y a continuación, encripta cada palabra del diccionario. Si el resultado de la encriptación de una palabra coincide con alguna de las que hay en el shadow significada que ha tenido éxito, imprimiendo la palabra utilizada como contraseña junto con el nombre del usuario. Además, al terminar imprime el tiempo que tardó y el número medio de contraseñas encriptadas por segundo.
Prueba el programa para verificar que funciona correctamente. Acuérdate de darle permisos de ejecución previamente.
$>
chmod +x pcrack.py$>
./pcrack.py shadow dict-$USER ...
Una vez que hemos comprobado que funciona, vamos a descargar un diccionario real y un fichero shadow mayor.
Antes debemos borrar el fichero shadow que hemos creado de ejemplo.
$>
rm shadow
$>
wget http://www.atc.uniovi.es/doctorado/6grid/data/dict.txt --2009-02-10 09:19:19-- http://www.atc.uniovi.es/doctorado/6grid/data/dict.txt Resolving proxy.uniovi.es... 156.35.14.6 Connecting to proxy.uniovi.es|156.35.14.6|:8888... connected. Proxy request sent, awaiting response... 200 OK Length: 745249 (728K) [text/plain] Saving to: `dict.txt' 100%[===========================================>] 745,249 --.-K/s in 0.1s 2009-02-10 09:19:20 (4.87 MB/s) - `dict.txt' saved [745249/745249]$>
wget http://www.atc.uniovi.es/doctorado/6grid/data/shadow --2009-02-28 13:00:41-- http://www.atc.uniovi.es/doctorado/6grid/data/shadow Resolving proxy.uniovi.es... 156.35.14.6 Connecting to proxy.uniovi.es|156.35.14.6|:8888... connected. Proxy request sent, awaiting response... 200 OK Length: 468 [text/plain] Saving to: `shadow' 100%[============================================================>] 468 --.-K/s in 0s 2009-02-28 13:00:41 (40,3 MB/s) - `shadow' saved [468/468]
Copiamos el diccionario a tecgrid01.epv.uniovi.es.
$>
globus-url-copy file:///$PWD/dict.txt gsiftp://$HOST/tmp/$USER/
Realizamos una petición al servidor de RLS para que establezca un mapeo entre el fichero que acabamos de transferir y un nombre lógico denominado dict-$USER.
$>
globus-rls-cli create dict-$USER gsiftp://$HOST/tmp/$USER/dict.txt rls://$HOST
Comprobamos que el servidor de RLS ha registrado el nombre lógico, tanto en el LRC como en el RLI.
$>
globus-rls-cli query lrc lfn dict-$USER rls://$HOST dict-ruf: gsiftp://tecgrid01.epv.uniovi.es/tmp/ruf/dict.txt$>
globus-rls-cli query rli lfn dict-$USER rls://$HOST dict-ruf: rls://tecgrid01.epv.uniovi.es:39281
A continuación vamos a crear otro programa denominado wrapper_pcrack. Este programa será el encargado de configurar el entorno de ejecución antes de ejecutar el programa pcrack.py. En concreto, establecerá las variables de entorno y transferirá el diccionario a la máquina donde se ejecute el programa.
$>
cat > wrapper_pcrack
#!/bin/sh echo "Execution on `hostname`" # Se establecen las variables de entorno source /opt/vdt/setup.sh # Se transfiere el diccionario a partir del nombre lógico ./getlfn.py dict-_USER_ rls://_HOST_ # Se ejecuta el programa ./pcrack.py shadow dict-_USER_
Sustitímos _USER_ y _HOST_.
$>
sed -i "s/_USER_/$USER/" wrapper_pcrack$>
sed -i "s/_HOST_/$HOST/" wrapper_pcrack$>
cat wrapper_pcrack #!/bin/sh echo "Execution on `hostname`" # Se establecen las variables de entorno source /opt/vdt/setup.sh # Se transfiere el diccionario a partir del nombre lógico ./getlfn.py dict-ruf rls://tecgrid01.epv.uniovi.es # Se ejecuta el programa ./pcrack.py shadow dict-ruf
Le debemos dar permisos de ejecución.
$>
chmod +x wrapper_pcrack
Debemos copiar al directorio actual el programa getlfn.py.
$>
cp ../rls/getlfn.py .
El siguiente paso va a consistir en crear el fichero de descripción del trabajo. Para enviar el trabajo vamos a utilizar Condor-G, por tanto, el formato del fichero de descripción será el que utiliza Condor.
$>
cat > pcrack.sub
Universe = grid grid_resource = gt4 $$(gatekeeper_url) $$(job_manager_type) requirements = (TARGET.gatekeeper_url =!= UNDEFINED) && \ (TARGET.job_manager_type =!= UNDEFINED) Executable = wrapper_pcrack output = pcrack.out error = pcrack.error log = pcrack.log should_transfer_files = YES when_to_transfer_output = ON_EXIT transfer_input_files = getlfn.py,pcrack.py,shadow Queue
Utilizamos el universo grid y como recurso grid gt4 (Globus GRAM versión 4). Además, indicamos que queremos utilizar cualquier elemento de computación que esté disponible. Estamos utilizando Condor-G para enviar el trabajo a una máquina Globus, y esta a su vez se lo va a enviar a un gestor de trabajos (en este caso coincide que es Condor). Cuando el trabajo se ejecute accederá al fichero de datos que se encuentra distribuido por nuestro grid.
Ya sólo nos queda la parte fácil, enviar el trabajo y esperar por los resultados.
$>
condor_submit pcrack.sub
Submitting job(s).
Logging submit event(s).
1 job(s) submitted to cluster 170.
Observamos la evolución de la ejecución del trabajo.
$>
condor_q -- Submitter: tecgrid03.epv.uniovi.es : <192.168.100.200:55623> : tecgrid03.epv.uniovi.es ID OWNER SUBMITTED RUN_TIME ST PRI SIZE CMD 170.0 ruf 2/10 09:38 0+00:00:00 I 0 0.0 pcrack_wrapper 1 jobs; 1 idle, 0 running, 0 held$>
condor_q -- Submitter: tecgrid03.epv.uniovi.es : <192.168.100.200:55623> : tecgrid03.epv.uniovi.es ID OWNER SUBMITTED RUN_TIME ST PRI SIZE CMD 170.0 ruf 2/10 09:38 0+00:00:00 I 0 0.0 pcrack_wrapper 171.0 ruf 2/10 09:38 0+00:00:01 R 0 0.0 gridftp_wrapper.sh 2 jobs; 1 idle, 1 running, 0 held
Como se puede observar, aparece un nuevo trabajo denominado gridftp_wrapper.sh. Este trabajo ha sido creado por Condor para realizar la transferencia de los ficheros utilizando GridFTP.
Comprueba los procesos que se han creado para ejecutar el trabajo.
$>
ps aux | grep condor
...
Uno de los procesos que aparece es condor_gridmanager, encargado de interactuar con los recursos grid.
Espera a que el trabajo termine (no te preocupes si gridftp_wrapper.sh sigue ejecutándose, terminará un rato después).
Comprueba el log del trabajo.
$>
cat pcrack.log
000 (098.000.000) 02/28 13:04:11 Job submitted from host: <156.35.171.92:44536>
...
017 (098.000.000) 02/28 13:04:40 Job submitted to Globus
RM-Contact: tecgrid01.epv.uniovi.es:9443
JM-Contact: https://156.35.171.90:9443/wsrf/services/ManagedExecutableJobService?e4659ba0-058f-11de-811a-a0c92eacbd7e
Can-Restart-JM: 0
...
027 (098.000.000) 02/28 13:04:40 Job submitted to grid resource
GridResource: gt4 tecgrid01.epv.uniovi.es:9443 Condor
GridJobId: gt4 https://156.35.171.90:9443/wsrf/services/ManagedExecutableJobService?e4659ba0-058f-11de-811a-a0c92eacbd7e
...
001 (098.000.000) 02/28 13:04:44 Job executing on host: gt4 tecgrid01.epv.uniovi.es:9443 Condor
...
005 (098.000.000) 02/28 13:05:42 Job terminated.
(1) Normal termination (return value 0)
Usr 0 00:00:00, Sys 0 00:00:00 - Run Remote Usage
Usr 0 00:00:00, Sys 0 00:00:00 - Run Local Usage
Usr 0 00:00:00, Sys 0 00:00:00 - Total Remote Usage
Usr 0 00:00:00, Sys 0 00:00:00 - Total Local Usage
0 - Run Bytes Sent By Job
0 - Run Bytes Received By Job
0 - Total Bytes Sent By Job
0 - Total Bytes Received By Job
...
Comprueba los resultados del trabajo, con un poco de suerte incluso es posible que hayas encontrado alguna contraseña.
$>
cat pcrack.out
...
Antes de terminar acuértate de borrar los ficheros que has subido a tecgrid01.epv.uniovi.es.
$>
globus-job-run $HOST /bin/rm -r /tmp/$USER