Ir al contenido principal

Renderizador de variantes varias de Mandelbrot

Pues eso, que he ampliado y traducido a C++ este script, debería ser bastante portable, todo es estándar (bueeeno,  los pthreads...), lo único que me preocupan son las tuplas que tenían una ruta curiosa ¿? enfin, que debería funcionar bien, la memoria está bastante pulida y tal ( aunque todos sabemos como son estas cosas xD ).

Se puede descargar de este repo [ https://gitorious.org/rand/ff ], compila con make (en Unix debería detectar solo el número de núcleos, en todo caso se puede especificar con -t <hilos>), se pueden ver los parámetros con ./ff -h, ahora algunas pruebas con los modos nuevos... ( las 3 primeras están rotadas 90 grados )

[caption id="attachment_920" align="aligncenter" width="580" caption="Buddhabrot: -a -i 1000 -m 100 -d 120 -r 10000000 -w 3000 -h 3000"][/ caption]

[caption id="attachment_921" align="aligncenter" width="580" caption="Anti buddhabrot: -aa -i 1000 -m 100 -d 120 -r 10000000 -w 3000 -h 3000"][/caption]

[caption id="attachment_922" align="aligncenter" width="580" caption="Buddhabrot Hologram: -ho -a -i 1000 -m 100 -r 100000000 -w 1200 - h 1200 -d 150"][/caption]

[caption id="attachment_926" align="aligncenter" width="600" caption="Julia basado en buddhabrot: -a -i 500 -m 100 -r 1000000 -j -1.1 0.1 -b"][/caption]

Y hay un par más subidas a deviantart ( de las que no recuerdo los parámetros :P )

http://kenkeiras.deviantart.com/art/Bodhi-bird-263712574

http://kenkeiras.deviantart.com/art/Anti-Buddhabrot-263741789

Eso es todo, hasta otra

[Referencias]

http://www.superliminal.com/fractals/bbrot/bbrot.htm

http://www.superliminal.com/fractals/bgram/bgram.html

Librería necesaria para instalar Freenet en Trisquel 5 [tip]

Después de 20 minutos buscando por qué fallaba ( no da error, solo no muestra el interfaz del instalador :P ), y antes de que le pase a alguien más: sudo apt-get install openjdk-6-jre

Ojalá todo fuera tan fácil de solucionar xD

Conocer en número de nucleos en Unix [C]

Muy rápidamente...

El número de nucleos de CPU se puede ver a través del directorio "/sys/ devices/system/cpu/", así que aprovechando que en Poesia_binaria_hay_un_post sobre_como_leer_directorios_en_C... aquí está un código que lee, la idea sería usar la función para usar el número correcto de hilos/procesos [getcpus.c]

include

include

include

include

define CPU_PATH "/sys/devices/system/cpu/"

int getCores(){

DIR *dir;

struct dirent* it;

int count = 0;

int i, isCpu;

dir = opendir(CPU_PATH);

if (dir == NULL){

exit(1);

}

while((it = readdir(dir)) != NULL){

if (strncmp(it->d_name, "cpu", 3) == 0){

isCpu = 1;

for(i = 3; it->d_name[i] != '\0'; i++){

if ((it->d_name[i] < '0')||(it->d_name[i] > '9')){

isCpu = 0;

break;

}

}

count += isCpu;

}

}

closedir(dir);

return count;

}

int main(int argc, char **argv){

printf("Encontrado(s): %i nucleo(s)\n", getCores());

return 0;

}

Hasta la próxima

Escribiendo un parser de Brainf*ck con BLK

¡Por fin! a estas alturas BLK permite compilar un razonable subset de C... bien, vale, faltan punteros y estructuras para tener algo decente, pero los primeros son escabrosos de simular con el intérprete, y las estructuras están en camino. Lo importante es que la estructura general es medianamente estable, aún dentro de la rama de prototipado, una consecuencia es que está abierto a cualquier participación :), así que veamos un ejemplo de como escribir un pequeño parser para brainf*ck.

Lo primero que haremos será importar el gestor de bytecode y preparar una constante para manejar el tamaño de la memoria, que en este caso será estática

from bytecode_manager import *

MEM_SIZE = 1024

El parser lo encapsularemos en una clase, con esta forma

class BrainfuckParser:

code = "" # Unparsed code

_bytecode_manager = None # Bytecode manager

global_frame = None # The global function

Ahora viene la función para inicializar la clase, recibe el gestor de bytecode como único parámetro

def init(self, bytecode_manager):

   self._bytecode_manager = bytecode_manager

Ahora tenemos que preparar un espacio para el código, el código se agrupa en frames (que vienen siendo como bloques en C, pueden representar funciones, bucles o condicionales), al menos uno es necesario para que el código sea ejecutable por el intérprete, llamemosle '_start'

self.global_frame = gframe = bytecode_manager.add_function("_start", void_type, [])

La sintaxis es: Bytecode_manager.add_function(, , )

Ahí dentro ya podemos definir variables y operaciones, creemos manualmente una variable cursor para controlar la posición en memoria, y asignémosle el valor 0

bytecode_manager.add_variable("cursor", int_type, gframe, "Cursor variable")

bytecode_manager.add_op(ASSIGNATION_OP, {"name": "cursor"}, 0, gframe)

Ahí tenemos dos funciones, la primera es Bytecode_manager.add_variable, recibe como parámetros el nombre de la variable, su tipo, el frame y opcionalmente un comentario sobre el uso de la variable. Bytecode_manager.add_op añade una operación al frame, el primer parámetro es el tipo de operación, el segundo una referencia a la variable donde se guardará el resultado, la tercera los parámetros (sería una lista si hay más de uno), y la cuarta el frame.

También podemos crear un nuevo tipo para representar nuestras variables, por ejemplo un array para la memoria, los tipos se representan como diccionarios con al menos el valor 'byte_size' que indica que cantidad de bytes se le dedicarán, además hay otros atributos que se pueden usar, como 'structure', que indica el tamaño de las dimensiones del tipo, por ejemplo [2, 3] para un array de 2x3

   tmp = {"byte-size": 4, "structure": [MEM_SIZE]}

   bytecode_manager.add_variable("mem", tmp, gframe, "Machine memory")

También se puede hacer lo mismo con las referencias a variables, si se indican con un diccionario se puede especificar en 'pos' que parte 'atacar'

def parse_brainfuck(self, frame):

   pointed_ref = {"name":"mem", "pos": ["cursor"]}

   cursor_ref = {"name":"cursor"}

El resto de la función parse no necesita de nada nuevo, solo operaciones ADD_OP y SUB_OP sobre las dos referencias que acabamos de definir, menos el '[' que mencinaremos a continuación

   while self.current < self.code_len:

       current_op = self.code[self.current]

       self.current += 1

       # Print

       if current_op == ".":

           self._bytecode_manager.add_op("putchar", {}, [pointed_ref],

frame, ".")

       # Read

       elif current_op == ",":

           self._bytecode_manager.add_op("getchar", pointed_ref, [],

frame, ",")

       # Inc

       elif current_op == "+":

           self._bytecode_manager.add_op(ADD_OP, pointed_ref,

[pointed_ref, 1], frame, "+")

       # Dec

       elif current_op == "-": self._bytecode_manager.add_op(SUB_OP,

pointed_ref, [pointed_ref, 1], frame, "-")

       # Push

       elif current_op == ">":

            self._bytecode_manager.add_op(ADD_OP, cursor_ref, [cursor_ref,

1], frame, ">")

       # Pop

       elif current_op == "<":

            self._bytecode_manager.add_op(SUB_OP, cursor_ref, [cursor_ref,

1], frame, "<")

       # While

       elif current_op == "[":

           b = self._bytecode_manager.add_branch(WHILE_BRANCH,

pointed_ref, frame)

           self.parse_brainfuck(b)



       # While-end

       elif current_op == "]":

           assert(frame != self.global_frame)

           return

Para añadir una operación de control de flujo utilizaremos Bytecode_manager.add_branch, pasandole como primer parámetro el tipo de ramificación (WHILE_BRANCH, IF_BRANCH, ELSE_BRANCH o DO_WHILE_BRANCH), el segundo parámetro es la condición, si es distinto de 0 se ejecuta el condicional o se sigue en el bucle, el tercero es el frame, además acepta otros dos más, uno para las operaciones que se realizarán antes de comprobar la condición, y el último para las operaciones que se realizaran antes de estas a partir del segundo paso (el paso del 'for'), esta operación devuelve un frame para añadir las operaciones que toman lugar dentro de el

b = self._bytecode_manager.add_branch(WHILE_BRANCH, pointed_ref, frame)

El resto del código es lo suficientemente genérico como para necesitar casi ninguna explicación

def parse(self, f):

   self.code = f.read()



   self.current = 0

   self.code_len = len(self.code)

   self.parse_brainfuck(self.global_frame)

if name=="main":

output = "a.blk"

if len(argv) < 2:

   print "%s " % argv[0]

   exit(0)

try:

   f = open(argv[1], "rt")

except:

   print "Error reading %s" % argv[1]

else:

   bm = BytecodeManager()

   bm.add_entry_point("_start")

   bfp = BrainfuckParser(bm)



   try:

       bfp.parse(f)



   except ParsingException, e:

       print "Parsing exception: %s" % e

       exit(2)



   bm.save(output)

Lo que si que se hace necesario mencionar es Bytecode_manager.add_entry_point que indica la función por la que entrar y Bytecode_manager.save para guardar el código

El código completo está aquí:

brainfuck_parser.py Hasta otra

Modificando `wardrive-android`

Bueno, pues aquí estamos, reestrenando blog :D

La aplicación Wardrive de android es una excelente herramienta para mapear redes con el móvil, que además está liberada bajo la licencia GNU GPLv3, en este post veremos como añadirle la opción de enviar la base de datos a un servidor web remoto.

Captura de la aplicación tomada del_repositorio

Lo primero que tenemos que hacer es descargar el código fuente, con svn checkout http://wardrive-android.googlecode.com/svn/trunk/ wardrive- android-read-only

Una vez hecho esto, lo abrimos con el IDE que prefiramos ( no me pararé a explicar como instalar los complementos para desarrollar para Android, se puede encontrar con una simple búsqueda ).

En el caso de NetBeans nos notificará que hay un problema, si hacemos click con el botón derecho en el proyecto y pulsamos en "Resolver problemas de referencia", dirá que '"Android_gapi_1.6" platform not found'. Si pulsamos en el botón resolver abrirá el gestor de plataformas, así que solo tenemos que seleccionar "Add platform".

El tipo de plataforma a instalar será "Google android ..."

A continuación tendremos que seleccionar la ruta al SDK

Y por último darle un nombre, "Android_gapi_1.6", y seleccionar la plataforma objetivo.

Una vez solucionados los problemas con el IDE, si no existe hay que crear un Dispositivo Android Virtual que incluya las API de Google, utilizadas para mostrar los mapas.

Ahora toca liarse con el código...

Primero añadiremos la opción de enviar los datos a la lista de opciones que se accede a través del Menú &gt; More. Este menú se encuentra en el archivo options_menu.xml, en el directorio /res/menu , debajo de la siguiente línea añadimos la misma modificada para nuestra opción:

El archivo quedaría por ejemplo así:

<item android:id="@+menu_id/SERVICE" android:title="@string/MENU_SERVICE_LABEL"

android:icon="@drawable/ic_menu_manage" />

<item android:id="@+menu_id/LIST" android:title="@string/MENU_LIST_LABEL"

android:icon="@drawable/ic_menu_mylocation" />

<item android:id="@+menu_id/STATS" android:title="@string/MENU_STATS_LABEL"

android:icon="@drawable/ic_menu_view" />

<item android:id="@+menu_id/PREFERENCES" android:title="@string/ MENU_OPTIONS_LABEL"

android:icon="@drawable/ic_menu_preferences" />

<item android:id="@+menu_id/QUIT" android:title="@string/MENU_QUIT_LABEL"

android:icon="@drawable/ic_menu_close_clear_cancel" />

<item android:id="@+menu_id/KML_EXPORT" android:title="@string/ MENU_KML_EXPORT_LABEL"

android:icon="@drawable/ic_menu_save">

<item android:id="@+menu_id/DELETE" android:title="@string/MENU_DELETE_LABEL" /

Además habría que añadir la cadena que tendría en cada idioma a los archivos string.xml, aunque con añadirlo a la que se muestra por defecto es suficiente en las pruebas dio problemas al añadirlo solo por defecto, aquí se explica el paso para ponerlo en inglés. Podemos encontrar los valores en el directorio /res/values-/ , buscamos la línea que contenga MENU_SEND_TO_WIGLE, y la copiamos modificando los valores necesarios, es decir, añadimos esta línea: Send wardrive.kml to server

Hecho esto, ya se muestra la opción, aunque lo único que hace es mostrar el 'about':

Lo que queda por cambiar es la acción que se toma al pulsar el botón, esto se define en el case de la función onOptionsItemSelecteddel archivomain.java, bajo este switch: switch (item.getItemId())

Añadimos nuestro case: case R.menu_id.SEND_TO_SERVER:

showDialog(Constants.DIALOG_SERVER_UPLOAD);

break;

Bien, vamos entonces con el diálogo, al switch de la función protected Dialog onCreateDialog(int id) (~línea 625 ), hay que añadirle un nuevo case que tome la URL y nos la pase a una función para manejarla: case Constants.DIALOG_SERVER_UPLOAD:

builder = new AlertDialog.Builder(this);

final EditText URIinput = new EditText(this);

URIinput.setText("");

builder.setView(URIinput);

builder.setPositiveButton(getString(R.string.OK), new DialogInterface.OnClickListener() {

   public void onClick(DialogInterface dialog, int whichButton) {

       String uri = URIinput.getText().toString().trim();

       send_to_server(uri);

   }

});

builder.setNegativeButton(getString(R.string.NO),

           new DialogInterface.OnClickListener() {



   public void onClick(DialogInterface dialog, int whichButton) {

       send_to_server(null);

   }

});

return builder.create();

Lógicamente hay que añadir un valor DIALOG_SERVER_UPLOAD a la clase Constants en Constants.java, como public static final int DIALOG_SERVER_UPLOAD = DIALOG_WIGLE_UPLOAD + 1;

Además hay que importar android.widget.EditText, que se utiliza en el Dialog.

Todo lo que queda por escribir es la función send_to_server(), que hace return si el string es null o envía el archivo a la url en un POST multipart, nombrandolo como 'wardrive'.
public void send_to_server(String url){

       if(url == null){

           return;

       }

       HttpClient httpclient = new DefaultHttpClient();

       HttpPost httppost = new HttpPost(url);



       File f = new File("/sdcard/wardrive.kml");

       try {

         MultipartEntity entity = new MultipartEntity();



         entity.addPart("wardrive", new FileBody(f));

         httppost.setEntity(entity);

         httpclient.execute(httppost);

       } catch (Exception e) {

       }

   }

Para esta función se requiere tener los .jar apache-mime4j, httpmime, httpclient y httpcore en el directorio de compilación e importar esto: import android.widget.EditText;

import org.apache.http.client.HttpClient;

import org.apache.http.impl.client.DefaultHttpClient;

import org.apache.http.client.methods.HttpPost;

import org.apache.http.entity.mime.MultipartEntity;

import org.apache.http.entity.mime.content.FileBody;

Nota: lógicamente hay que exportar el KML antes de enviarlo al servidor

El código fuente resultante: wardrive-mod.zip

Y compilado: wardrive.apk

Y eso es todo, nos vemos. [Referencias] http://code.google.com/p/wardrive-android/ http://www.softwarepassion.com/android-series-get-post-and-multipart-post- requests/ https://code.google.com/p/androidmcr/source/browse/trunk/MCR/apache-mime4j- 0.6.jar?r=85 https://code.google.com/p/google-secure-data-connector/source/browse/trunk/ data-connector-agent/third-party/httpcomponents-client-4.0.1/httpmime- 4.0.1.jar?r=525

Como hacer las imagenes que ponen ip, navegador...

Para esto necesitaremos un servidor HTTP ( como apache ) y PHP, las dos cosas es lo tipico que se encuentra en un hosting gratuito ( aqui hay una lista )

Si lo vamos a alojar nosotros mismos necesitaremos habilitar el paquete php-gd para esto edita el php.ini, descomenta la linea de ";extension=php_gd2.dll" (quitale el ';'... en algunos casos es un '#') En debian/ubuntu se hace con "sudo apt-get install php5-gd"

Vamos alla...

Buscamos una imagen, la imagen sera la base, conviene que sea lo mas uniforme posible para que quede bien, yo escogí esta, aun que no sea la mas apropiada

Preparamos el codigo en PHP

El siguiente codigo es el que escribira en la imagen <?php

// Escrito por Kenkeiras

function navegador($ua){ //  Devuelve el navegador ...bastante simple ;)

$nav="";

if (strstr($ua,"Firefox"))

$nav="Firefox";

elseif (strstr($ua,"MSIE 6"))

$nav="IExplorer 6";

elseif (strstr($ua,"MSIE 7"))

$nav="IExplorer 7";

elseif (strstr($ua,"MSIE 8"))

$nav="IExplorer 8";

elseif (strstr($ua,"Opera"))

$nav="Opera";

elseif (strstr($ua,"Safari"))

$nav="Safari";

return $nav;

}

function os($ua){ // lo mismo, pero para el SO

$os="";

if (strstr($ua,"Linux"))

$os="Linux";

elseif (strstr($ua,"Windows"))

$os="Windows";

elseif (strstr($ua,"Mac"))

$os="Mac";

return $os;

}

$back="esfera.png";   //Imagen de fondo

$img=imagecreatefrompng($back);   //Se crea la imagen  (desde un png)

$fcolor=ImageColorAllocate($img,255,120,0); //  El color de las letras ($img,r,g,b)

// Ejemplo: ImageString ($img,Tamaño de letra,Longitud,Altura,"Texto",$fcolor);

$ip=$_SERVER['REMOTE_ADDR'];  // La ip esta en la variable $_SERVER['REMOTE_ADDR']

ImageString($img,5,65,75,"IP: $ip",$fcolor); //  Escribimos la IP en la imagen

$lang=$_SERVER['HTTP_ACCEPT_LANGUAGE'];

$i=stripos($lang,";");

if ($i)

$lang=substr($lang,0,$i);

if ($lang!="")

ImageString($img,5,50,100,"Lenguaje: $lang",$fcolor);

$ua=$_SERVER['HTTP_USER_AGENT'];

$os=os($ua);

$nav=navegador($ua);

if ($nav!="")

ImageString($img,5,40,125,"Navegador: $nav",$fcolor);

if ($os!="")

ImageString($img,5,35,150,"Sistema Operativo: $os",$fcolor);

// ----------------

Header("Content-Type: image/png");  //  Avisamos que es una imagen png

ImagePNG($img);            //  Convertimos a png

// Si prefieres un JPEG cambia las dos ultimas lineas por

//Header("Content-Type: image/jpeg")

//ImageJPEG($img);

// ----------------

ImageDestroy($img);   // Liberamos el espacio

?>

Como funciona? (Para l@s que no les guste leer los comentarios del codigo)

Se usan dos funciones (navegador y os), que buscan en la cadena del "User- Agent", alguna parte conocida (Firefox, MSIE, etc...), y que devuelven el navegador y el sistema operativo del usuario

El resto es PHP,

$back="esfera.png"; //Imagen de fondo $img=imagecreatefrompng($back); //Se crea la imagen (desde un png)

Como indican los comentarios, la primera linea es saber donde esta la imagen base, la segunda es para importarla como PNG, tambien se puede hacer para jpg

imagecreatefromjpeg

o con gif

imagecreatefromgif

(aqui hay mas funciones parecidas: http://us3.php.net/manual- lookup.php?pattern=imageCreateFrom&lang=es)

$fcolor=ImageColorAllocate($img,255,120,0); // El color de las letras ($img,r,g,b)

Prepara el color de las letras en la imagen (recuerda que la imagen esta en $img), el color se asigna en rgb, de 0 a 255 (esta combinacion, "255,120,0", seria naranja)

$ip=$_SERVER['REMOTE_ADDR']; //La ip esta en la variable

Guarda la ip (que esta en la variable $_SERVER['REMOTE_ADDR'])

ImageString($img,5,65,75,"IP: $ip",$fcolor);

Escribe en la imagen, con tamaño de letra 5, desde el pixel 65 (horizontal) y el 75 (vertical), la cadena "IP: $ip",en el color $fcolor

El resto es hacer lo mismo con lo que nos interesa (lenguaje, navegador,etc...)

Y despues

Header("Content-Type: image/png"); // Avisamos que es una imagen png

Avisamos al navegador para que reconozca lo que viene ahora como una imagen png (si es jpg, habria que poner "image/png")

Y los dos ultimos pasos

ImagePNG($img); // Convertimos a png ImageDestroy($img); // Liberamos el espacio

Resultado:

Suerte y hasta otra

Gráficos de tortuga sobre imágenes en Python

Pues hoy traigo una mini-libraría que se apoya en PIL para hacer gráficos de tortuga directamente sobre imágenes [ imgturtle.py ]: 

Dibujado con este script [  dragon.py ]

La idea es que se acerque lo máximo posible a la implementación oficial de los gráficos_de_tortuga_de_python con el añadido de poder guardar las imágenes ( y más velocidad me atrevería a decir ).

Al comenzar hay que crear un objeto imgturtle, que maneja la imágen, al inicializar el objeto se debe pasar un parámetro, una tupla de números que defina el tamaño en 'x' y en 'y' de la imágen o bien una cadena con el nombre del archivo del que se va a partir:

t = imgturtle( ( x, y ) ) # Nueva imágen

t = imgturtle( argv[ 1 ] ) # Imágen basada en otra

Una vez creado el objeto se puede disponer de los métodos habituales de estos gráficos:

imgturtle.clear( ): # Vuelve a la imágen original

imgturtle.reset( ): # Reinicia la tortuga

imgturtle.save( fname ): # Guarda la imágen

imgturtle.rt( angle ): # Gira a la derecha con un ángulo || imgturtle.right()

imgturtle.lt( angle ): # Gira a la izquierda con un ángulo || imgturtle.left ()

imgturtle.fd(  steps ): # Avanza unos pasos || imgturtle.forward()

imgturtle.bk( steps ): # Retrocede unos pasos || imgturtle.backward( )

imgturtle.pu( ): # Levanta el lápiz

imgturtle.seth( angle ): # Establece el ángulo ||imgturtle.setheading()

imgturtle.goto( x, y ):    # Se mueve hasta una posición

imgturtle.pencolor( color ): # Establece el color que se pinta

imgturtle.home( ): # Vuelve a la posición inicial

imgturtle.pd( ): # Baja el lápiz || imgturtle.pendown() imgturtle.down()

imgturtle.pu( ):# Levanta el lápiz || imgturtle.penup() imgturtle.up()

imgturtle.heading( ): # Devuelve el ángulo de la tortuga

imgturtle.pos( ):# Devuelve la posición de la tortuga ||  imgturtle.position()

Nota: el sistema de coordenadas no está centrado en ( 0, 0 ), sinó en x / 2, y / 2

imgturtle.isdown( ): # Si el lápiz está bajado

Y eso es todo, por último un ejemplo dibujando sobre una imágen ya existente [ rayar.py ]. Original:

Después de "$ ./rayar.py base.png out.png":

Hasta otra

Recuperar una "HOME" cifrada desde un live cd

Supongamos que hemos cifrado la carpeta de usuario (Trisquel y Ubuntu dan esa posibilidad al instalarlo), y por cosas de la vida perdemos la posibilidad de acceder al SO, pero seguimos teniendo acceso a la particion con los datos (  y la clave, se entiende ). Esto es lo que podríamos hacer desde un LiveCD para volver a montar la partición:

Nota: substituye $DRIVE por la ruta hacia la particion home + .ecryptfs, por ejemplo sería /media/blablabla/.ecryptfs/

[ 1 ] Obtener clave del sistema de cifrado, contenida en $DRIVE/<nombre de usuario>/.ecryptfs/wrapped-passphrase , y envuelta con la contraseña del usuario.

1
2
3
$ ecryptfs-unwrap-passphrase $DRIVE/<nombre de usuario>/.ecryptfs/wrapped-passphrase
Passphrase: # Aqui la clave del usuario
e25c829b60e65e63a1ec2b9581ae4d4a

Entonces e25c829b60e65e63a1ec2b9581ae4d4a sería la clave con la que se cifraron los datos, pero queda otra, a partir de Ubuntu 9.04 se cifran por defecto tambié los nombres de archivo.

[ 2 ] Obtener la clave que cifra los nombres de los archivos.

1
2
3
4
$ ecryptfs-add-passphrase --fnek
Passphrase: # La clave que acabamos de obtener
Inserted auth tok with sig [b6829c7b365a3b16] into the user session keyring
Inserted auth tok with sig [b906f5e58bfbce18] into the user session keyring

La segunda, b906f5e58bfbce18, es la que cifra los nombres de los archivos.

[ 3 ] Montar el sistema de archivos.

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
$ sudo mount -t ecryptfs $DRIVE/<nombre de usuario>/.Private/ /home/<nombre de usuario>/
Passphrase: # Clave de cifrado de los archivos
Select cipher:
1) aes: blocksize = 16; min keysize = 16; max keysize = 32 (not loaded)
2) blowfish: blocksize = 16; min keysize = 16; max keysize = 56 (not loaded)
3) des3_ede: blocksize = 8; min keysize = 24; max keysize = 24 (not loaded)
4) cast6: blocksize = 16; min keysize = 16; max keysize = 32 (not loaded)
5) cast5: blocksize = 8; min keysize = 5; max keysize = 16 (not loaded)
Selection [aes]: aes # Por defecto
Select key bytes:
1) 16
2) 32
3) 24
Selection [16]: 16 # Por defecto
Enable plaintext passthrough (y/n) [n]: n # Por defecto

# Atencion a partir de aqui ;) 
Enable filename encryption (y/n) [n]: y # Si, desde la Ubuntu 9.04 los nombres de archivo están cifrados
Filename Encryption Key (FNEK) Signature [b6829c7b365a3b16]: b906f5e58bfbce18 # Clave de cifrado de los nombres
Attempting to mount with the following options:
ecryptfs_unlink_sigs
ecryptfs_fnek_sig=b906f5e58bfbce18
ecryptfs_key_bytes=16
ecryptfs_cipher=aes
ecryptfs_sig=b6829c7b365a3b16
WARNING: Based on the contents of [/root/.ecryptfs/sig-cache.txt],
it looks like you have never mounted with this key
before. This could mean that you have typed your
passphrase wrong.

Would you like to proceed with the mount (yes/no)? : yes # Para montarlo aunque no esté entre las claves utilizadas
Would you like to append sig [b6829c7b365a3b16] to [/root/.ecryptfs/sig-cache.txt]
in order to avoid this warning in the future (yes/no)? : yes # Para que no muestre que es una clave nueva si lo montamos otra vez
Successfully appended new sig to user sig cache file

Mounted eCryptfs

Ya está!

Y, aunque no sea necesario decirlo, para desmontar el sistema de archivos al final:

1
$ sudo umount /home/<nombre de usuario>/

Hasta otra

Ojo con las @ en las url

Cuidado con ellas, que el navegador piensa que lo que va antes es el usuario [ y contraseña ] para acceder a la pagina, algo como http://google.es: blablabla@codigoparallevar.co.cc/blog.

Si entras en esa pagina acabaras en codigoparallevar.co.cc, y con un blablabla algo extenso puede pasar por un link legítimo, curiosamente distintos navegadores reaccionan de distinta forma:

* Firefox 6.0.2 release: muestra un popup con el texto 'Está a punto de
iniciar sesión en el sitio "codigoparallevar.co.cc" con el nombre de
usuario "google%2Ees", pero el sitio web no requiere autenticación. Es
posíble que esto sea un intento de engaño'.

* Midori 0.2.4, Chromium 12, links2 y Chrome(por piou) : no muestra
ningún aviso y en la url no muestra lo que hay antes del @.

* Lynx: Muestra un aviso 'Alert!: Address contains a username: google.es:
blablabla' mientras carga, después lo muestra ( en este caso no se
muestra la URL ).

* Opera (por helq): No muestra ningún mensaje.
*
* Elinks (por mungu): no muestra nada
*

Sabeis como reaccionan otros navegadores?

El hackmeeting de este año es en A Coruña

**** Hackmeeting@A_Corunha ****

**** 21, 22 y 23 de Octubre ****

 
**** ¿Qué es Hackmeeting? ****


=====================================================================


Hackmeeting es un encuentro libre y autogestionado que gira en torno
a las nuevas tecnologías, sus implicaciones sociales, la libre
circulación de saberes y técnicas, la privacidad, la creación
colectiva, el conflicto telemático... Está destinado a todo tipo de
personas que tengan una mente abierta y curiosa con ganas de
compartir sus experiencias y vivirlo participando en la coordinación
como una más. Algunas charlas y talleres exigen conocimientos
informáticos avanzados, otros no; y otros ni informáticos.

( Sacado_del_Wiki )

El hackmeeting de este año se celebra en A Coruña ( que a mano que me queda! ^^ ), ya hay propuesto_un_nodo_sobre_IPv6 y hay información varia en el Wiki.

Ahí nos vemos... a ver si saco tiempo para proponer un nodo sobre redes anónimas :)