Por fin nos libramos de las patentes de software

Después de haber luchado incansablemente por que las patentes de software no salgan adelante, después de haber explicado sus contras, después de habernos llevado grandes disgustos y pequeñas alegrías, por fín puedo decir que la propuesta de patentes de software en Europa ha sido definitivamente derogada contundentemente por 648 votos a favor, 14 en contra y 18 abstenciones.

¡¡¡ Estamos de Enhorabuena !!!

Wake On LAN y Magic Packet

Todos sabemos que podemos apagar el ordenador con un comando o bién con una combinación de pulsaciones de teclado o ratón, también hay programas que dado cierto evento hacen que se apague el sistema.

Esto no tiene ningún misterio, pero… ¿y si se trata de encenderlo?. Puede que con el solo hecho de pulsar el botón de encendido de la cpu nos sea suficiente (a veces con pulsar un botón del teclado o mover el ratón), sin embargo cuando no estamos físicamente presentes la cosa cambia: un cibercafe donde es más cómodo encender todos los ordenadores a la vez, o encender un ordenador remoto que por las noches se apaga para ahorrar electricidad, etc. Antiguamente los ordenadores se apagaban y punto, pero desde que irrumpió en el mercado el formato ATX de cajas y placas madre y con el estandar ACPI la cosa no ha hecho más que facilitarnos las cosas: ahora gracias a esos dos estandares somos capaces de apagar el ordenador por software, apagar el equipo ordenadamente por hardware, suspender, volver a reactivar, volver a encender, etc. En la parte que nos toca hay unos eventos que son capaces de encender un ordenador cuando este está apagado, y para la gestión remota de ese encendido se puede usar unos metodos denominados wake on ring, wake on modem (por modem) o wake on lan (por red).

Este artículo se centra en el método Wake On Lan (+ o – despertar por red). Este sistema se basa en que un ordenador cuando se apaga, no lo hace totalmente, sino que la fuente de alimentación sigue alimentando a la placa madre, y esta puede gestionar con muy bajo consumo los eventos que se den, como por ejemplo, encender el ordenador cuando recibe un paquete especial por la tarjeta de red. Este paquete, conocido como Magic Packet es muy simple y su formato consiste en 6 bytes con valor hexadecimal FF y otros 16 grupos de 6 bytes con la dirección MAC de la tarjeta de red. Da igual en que protocolo se envié ese paquete (IPX, TCP/IP, etc), con tal de que se envíe por toda la red. Así si se quiere encender un ordenador con una MAC 01:02:03.04:05:06 se enviaría un paquete con estos bytes en hexadecimal:

FFFFFFFFFFFF
010203040506010203040506010203040506010203040506
010203040506010203040506010203040506010203040506
010203040506010203040506010203040506010203040506
010203040506010203040506010203040506010203040506

El paquete debe enviarse a toda la red, por lo que hay que intentar que sea con el protocolo que se haga, este debe permitir enviar paquetes broadcast. Esto normalmente se puede conseguir con el protocolo IP, ya que poniendo como destinatario la dirección IP 255.255.255.255 debería llegar a todos los nodos de todas las redes que lo permitan. El TCP o UDP que venga por encima no es importante, aunque personalmente prefiero el UDP por no ser orientado a conexión. Por encima del UDP vendrá el magic packet. A continuación pongo un ejemplo de codigo fuente en varios lenguajes de programación para que podais probarlo (son tan cortos que no hacen falta comentarlos, tampoco tienen gestión de errores para su simplicidad), en vuestro caso solo tendrías que modificar el puerto (1976) y la dirección MAC (01:02:03:04:05:06):

C para Linux/Unix y Windows

Perl

Java

Visual Basic (Para que funcione debeis insertar un control Winsock)

Por supuesto no hay método que sirva para marcar todas las tarjetas a la vez, así que habrá que ir una por una mandando el magic packet para que se vaya encendiendo cada ordenador. La tarjeta de red de cada ordenador apagado compara todos los paquetes que le llegan del tráfico de red para ver si contiene 16 veces su dirección MAC y así mandar a la placa madre que encienda el ordenador.

Las tarjetas de red que vengan incorporadas ya de fábrica en la placa madre ya tienen esta función activada. Sin embargo las que estan sueltas en ranuras PCI o ISA, deben:
1) Permitir el wake on lan (no todas tienen un firware con esa posibilidad)
2) La placa madre debe tener un conector de 3 pines que permita este evento.
3) Un cable que vaya desde la tarjeta hasta la placa madre.
En ambos casos se debe activar en la BIOS el mantenimiento de energía y posteriormente el evento WAKE ON LAN.

En mi portatil no puedo probar esta característica (cuando se apaga este, la tarjeta ethernet incorporada también se apaga). En el ordenador de sobremesa no me ha funcionado (tampoco funcionan eventos como el de encender el ordenador con una pulsación del teclado) y con el servidor me ha funcionado perfectamente.

El Magic Packet también se puede hacer desde Internet:
Si teneis conexión directa solo debeis modificar vuestro programa para que apunte a vuestra IP pública de Internet (si no es fija podeis usar cosas como dyndns).
Si no teneis conexión directa o no quereis usar un programa, podeis hacerlo desde aquí.
Sin embargo, a no ser que tengais un router que este conectado a Internet y donde podais poner rutas estáticas con IP, puertos y direcciones MAC no podreis hacerlo funcionar, ya que el router (como el mio) borra de la tabla arp las relaciones MAC/IP cuando detecta que no hay tráfico en una tarjeta determinada, por lo que aunque reciba un paquete que luego deba reenviar a una ip interna, lo ignora al no encontrarlo en la tabla; tampoco tiene opción para redireccionarlo como broadcast dentro de la red si no sabe que hacer con el.

Ejecutar un programa sin sistema operativo

Todo pc ejecuta código máquina: Ya sea en el arranque (La bios no es más que código máquina), en la carga del sistema operativo (el kernel esta programado en su mayor parte en código maquina) y en la ejecución de programas (el código fuente compilado o interpretado se transforma de una u otra manera en código máquina). Esta forma de trabajar hace que realmente no sea necesario un sistema operativo para ejecutar aplicaciones (y si me lo poneis dificil, hasta tampoco haría falta la bios). Es por ello que hay aplicaciones como los gestores de arraque (lilo, grub, nt loader), virus, etc que no necesitan de un sistema operativo para funcionar.

Siguiendo este camino, cualquiera podría crear una aplicación que, manteniendola y añadiendola nuevas funcionalidades, podría convertirse en el kernel que Linus Torvalds desarrolló de minix y que posteriormente se transformaría en linux.

Mi intención esta lejos de desarrollar un sistema operativo propio… aún :-), sin embargo a continuación pongo una aplicación, que ejecutada desde un disquete nada más arrancar el pc, muestra un menú y realiza operaciones básicas (chorras). Necesitareis un disquete ya formateado, el programa debug del msdos (por defecto en todos los windows) y que como primera unidad de arranque del pc sea la disquetera (próximamente hablaremos de como pasarlo a un cd mediante el estandar «el torito»). Para los linuxeros de pc, próximamente pondré algo parecido al rawrite. Las instrucciones para hacerlo funcionar son las siguientes:

1-cargad una consola msdos (en windows 9x: inicio/ejecutar/command, en windows nt,2000 o xp: inicio/ejecutar/cmd)

2-Insertad un disquete ya formateado en la disquetera y que no tenga nada importante (ya que perdereis toda la información que contuviera)

3-copiad el siguiente texto a un fichero de texto en vuestro disco duro (dejad al final un retorno de carro), por ejemplo codigo.txt:

a
jmp 1f7
db ‘Seleccione una opcion del menu’
db ‘1- Mostrar hora’
db ‘2- Coche Fantastico’
db ‘3- Salir’
db ‘Desarrollado por Oscar Rodriguez http://sistemasorp.blogspot.com’
db ’00:00:00′
db ‘Fijese en las luces del teclado’
db ‘Retire el disco o cd de la unidad de arranque y pulse una tecla’
cli
xor ax,ax
mov ss,ax
mov sp,7c00
mov es,ax
mov ds,ax
sti
mov ah,0
mov dl,0
int 13h
mov ax,201
mov bx,7e00
mov cx,2
xor dx,dx
int 13h
mov ax,3
int 10h
mov ax,1001
mov bh,1
int 10h
mov ax,1300
mov bx,2
mov cx,1e
mov dx,0119
mov bp,7c03
int 10h
mov ax,1300
mov bx,2
mov cx,0f
mov dx,0519
mov bp,7c21
int 10h
mov ax,1300
mov bx,2
mov cx,13
mov dx,0619
mov bp,7c30
int 10h
mov ax,1300
mov bx,2
mov cx,8
mov dx,0719
mov bp,7c43
int 10h
mov ax,1300
mov bx,4
mov cx,46
mov dx,1705
mov bp,7c4b
int 10h
mov ah,0
int 16h
push ax
mov ax,700
mov bh,0
mov cx,0900
mov dx,094f
int 10h
pop ax
cmp ah,2
je 29f
cmp ah,3
je 2fd
cmp ah,4
jne 29d
jmp 32f
jmp 278
mov ah,2
int 1ah
push cx
mov bx,7c91
mov al,ch
mov cl,4
shr al,cl
add al,30
mov [bx],al
inc bx
mov al,ch
and al,0f
add al,30
mov [bx],al
add bx,2
pop cx
mov ch,cl
mov al,ch
mov cl,4
shr al,cl
add al,30
mov [bx],al
inc bx
mov al,ch
and al,0f
add al,30
mov [bx],al
add bx,2
mov al,dh
mov cl,4
shr al,cl
add al,30
mov [bx],al
inc bx
mov al,dh
and al,0f
add al,30
mov [bx],al
mov ax,1300
mov bx,7
mov cx,8
mov dx,0919
mov bp,7c91
int 10h
jmp 278
mov ax,1300
mov bx,7
mov cx,1f
mov dx,0919
mov bp,7c99
int 10h
mov cx,3
mov ah,2
call 346
mov ah,4
call 346
mov ah,1
call 346
mov ah,4
call 346
loop 311
mov ah,0
call 346
jmp 278
mov ax,1300
mov bx,7
mov cx,3f
mov dx,0908
mov bp,7cb8
int 10h
mov ah,0
int 16h
int 19h
push cx
cli
mov al,ed
out 60,al
in al,64
test al,2
loopnz 34c
mov al,ah
out 60,al
sti
mov ah,0
int 1ah
mov bx,dx
add bx,9
mov ah,0
int 1ah
cmp bx,dx
jnz 360
pop cx
ret

w 100 0 0 2
q

4-Ejecutad el siguiente comando: debug < codigo.txt

5-Reiniciad el ordenador con el disquete dentro

Este proceso lo que hace es ejecutar tanto comandos del debug del msdos, como intrucciones en ensamblador. Con esto guardamos en el sector de arranque del disquete (no del disco duro) un programa que se ejecutará nada más reiniciar el ordenador, antes de que se cargue el sistema operativo. Este programa tiene un menú con 3 opciones:
1- Mostrar hora: Muestra la hora actual del sistema.
2- Coche Fantastico: Simula las luces del coche fantástico en los led del teclado
3- Salir: Sale del programa, cuando se retira el disquete carga el sector de arranque del disco duro.

Con este programa se muestra todo lo que que se puede necesitar de un pc:
-interfaz con el usuario de entrada (teclado)
-interfaz con el usuario de salida (monitor)
-lectura de disco (lectura del resto del programa en otro sector)
-gestión de memoria (las cadenas de texto y la pila)
-gestión de dispositivos (luces de teclado)

Las instrucciones del debug son:
a: introducir código en ensamblador.
w 100 0 0 2: escribir el programa en los primeros sectores de arranque del disquete desde la posicion de memoria 100.
q: salir del debug.

No voy a explicar que hace cada cosa en el programa, sin embargo si alguien tiene dudas puede preguntarme que significa cualquier parte del código en ensamblador. A grosso modo usa las funciones de la bios para poder funcionar: la interrupción 10h la uso para mostrar cadenas, la interrupción 13h para leer un segundo sector del disquete, la interrupción 16h para leer caracteres pulsados del teclado, la interrupción 19h para reiniciar el sistema sin tener que testearlo todo de nuevo, la interrupción 1ah para hacer retardos y averiguar la hora del sistema. Escribo en el puerto 60 para modificar el estado de los leds del teclado. Su arquitectura se basa en la peculiaridad de la bios de guardar nada más arrancar el primer sector del disquete en la zona de memoria 0000:7C00 y luego enviar la ejecución a ese punto.

El hecho de haber usado la herramienta debug es porque lo tiene todo el mundo en su windows. Sin embargo no esta orientada a usarse para programar sectores de arranque, más bién para editarlos, editar ficheros o crear ficheros ejecutables con extensión .COM; por este último motivo he tenido que ir jugando con los saltos relativos a pelo, es decir, como los programas en debug empiezan en el desplazamiento 100h de la memoria (típico de los ficheros .COM) he estado poniendo los destinos de los saltos en base a esa posición 100h, por lo que cuando he necesitado modificar una instrucción, he tenido que cambiarlos también. Por suerte al ser saltos relativos (e internamente el debug los convierte así) no influye en el resultado final.

Por último si teneis curiosidad por el mundo del pc y sus interioridades, saber como es el proceso de arranque del pc, cambiar las luces del teclado y muchísimo más, teneis el maravilloso y gratuito libro EL UNIVERSO DIGITAL DEL IBM PC, AT Y PS/2 de Ciriaco García de Celis, el cual explica con mucho detalle las tripas de los pcs.

Gateway SMS/EMAIL/SMS

Bueno, pues hoy voy a enseñar un pequeño proyecto el cual ya hace tiempo que había terminado, pero que hoy doy a la luz pública (en fase beta) para que lo probeis a ver que os parece.

La idea de hacer un gateway sms2email y email2sms hacía tiempo que me rondaba la cabeza. Mi idéa era hacerlo bajo linux, ya que es el mejor sistema operativo que puede hacer de servidor y para este caso en concreto necesitaba un servidor POP3 y SMTP. Segundo necesitaba un aparato que enviase y recibiese sms, por lo que aproveché mi antiguo Siemens M35 y un cable de datos que ya tenía anteriormente para que hiciese las veces de servidor sms. Tercero necesitaba el software que gestionase los sms y los correos, por lo que para el primer caso usé la estupenda herramienta SMS server tools cuyo funcionamiento se reduce a guardar en un directorio un archivo con formato por cada sms nuevo del móvil, y enviar un sms por cada archivo con formato que encuentre en otro directorio; para el segundo caso he usado el perl con las librerias Net::POP3, Net::SMTP, MIME::Parser, MIME::Entity y MIME::Body.

El resultado final es el siguiente que os explico:

Para enviar un correo y que se transforme en sms:
-En el destinatario del correo poneis sms@sistemasorp.com
-En el asunto del correo poneis SOLO el número de teléfono con prefijo 34 o sin el (no acepta mensajes a móviles que no sean de España).
-En la primera línea del mensaje poneis el texto que querais siendo menor de 140 carácteres.

Para enviar un sms y que se transforme en mail:
-Poner la dirección de correo electrónico seguido de un espacio y el texto del mensaje.
-Enviadlo al número de móvil 699744630. Esto os costará lo que vuestro proveedor de telefonía móvil os cobre por un sms normal y corriente (normalmente 15 céntimos de euro).

En el caso de que sea mi sistema el que envíe el sms después de recibir un correo, me costará 15 céntimos de euro, aunque como estoy probando el sistema y el sim que tengo es de los que tienen dinero aún acumulado por la promoción de compra de un nuevo móvil, no me importa que se gaste. Más adelante lo pondré con contraseña para que solo yo o la gente que decida puedan usarlo.

El código fuente en perl no esta aún comentado, aunque si quereis una copia, podeis pedirmela sin problemas.

Los mensajes sms pueden recibirse o enviarse inmediatamente, tardiamente o nunca, eso ya depende de los proveedores de telecomunicaciones, de vuestro servidor de smtp tenga la última ip de mi dominioa través del DNS que use, etc.

Comprimir la salida de un php

Cuando hacemos una página en php, normalmente la solemos hacer para que muestre contenido de texto ya formateado (en html si es para un navegador, en xml si es para un servicio web, etc). Cuando digo formateado me refiero a que no solo contiene contenido textual, sino que también contiene etiquetas de formato, etiquetas pertenecientes al tipo de documento, comentarios, códigos, etc. Esto al final provoca que haya mucha saturación en cuanto a contenido, o dicho de otra forma, se envían muchos bytes.

El problema radica en que por un lado se esta gastando un ancho de banda que pudiera servir para otras cosas (como es el caso de los hosting, donde tiene un limite de transferencia mensual) y al mismo tiempo provoca que se tarde más tiempo en descargar esa información (especialmente si estamos hablando de modems).

La solución pasa por comprimir la salida del php y que el navegador del cliente se encargue de descomprimirla. Para ello hace ya tiempo que se añadió al estardar HTTP 1.1 la cabecera Accept-Enconding. Esta cabecera es enviada por el navegador al servidor web y contiene una lista de métodos de codificación de contenido que el navegador puede tratar. En el caso del Firefox o del Internet Explorer esta lista es gzip y deflate. El gzip es el método que nos interesa, ya que con el, se comprime la salida. Así que si el navegador pide al servidor un página php (y esta permite comprimirla como veremos a continuación), el documento que el servidor entrega al navegador estará comprimido (con una cabecera a su vez denominada Content-Encoding), con el consecuente ahorro de tiempo de transferencia y cantidad de datos a transmitir. Teniendo en cuenta que casi siempre suele ser texto lo que se envía, la compresión se hace mucho mejor, ya que se repite mayor cantidad de carácteres.

Ejemplo de petición del navegador Firefox:
GET /divisas/divisas.php HTTP/1.1
Host: www.quejateportodo.com
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; es-AR; rv:1.7.5) Gecko/20041108 Firefox/1.0
Accept: text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5
Accept-Language: es-ar,es;q=0.8,en-us;q=0.5,en;q=0.3
Accept-Encoding: gzip,deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 300
Connection: keep-alive

Ejemplo de petición del navegador Internet Explorer:
GET /divisas/divisas.php?idioma=es&fecha=09/04/2005&version=201&codigo=21988 HTTP/1.1
Accept: */*
Accept-Encoding: gzip, deflate
User-Agent: Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1; SV1; .NET CLR 1.1.4322)
Host: www.quejateportodo.com
Connection: Keep-Alive
Cookie: PHPSESSID=09b4f65e7adf47e857a309d5a9ef83e3

A lo que en mi caso el servidor devuelve esta respuesta similar en ambos casos:

HTTP/1.1 200 OK
Date: Sat, 09 Apr 2005 16:49:14 GMT
Server: Apache/1.3.33 (Unix) mod_gzip/1.3.26.1a mod_auth_passthrough/1.8 mod_log_bytes/1.2 mod_bwlimited/1.4 PHP/4.3.10 FrontPage/5.0.2.2635 mod_ssl/2.8.22 OpenSSL/0.9.7a
X-Powered-By: PHP/4.3.10
Expires: Mon, 26 Jul 1997 05:00:00 GMT
Cache-Control: no-store, no-cache, must-revalidate
Pragma: no-cache
Last-Modified: Sat, 09 Apr 2005 16:49:14 GMT
Cache-Control: post-check=0, pre-check=0
Content-Encoding: gzip
Vary: Accept-Encoding
Content-Type: text/xml
Age: 496
Connection: close

Y después de tanta teoría, la práctica:

<?
ob_start(«ob_gzhandler»);

… Aquí se mete toda la lógica del php …

ob_end_flush();
?>

¿A que resulta muy curioso que sea tán extremadamente sencillo el hacerlo?. Primero ponemos al principio del todo de la página php la instrucción ob_start del php, que sirve para activar el modo «buffering», que no es otra cosa que primero genera la página y luego la envia en vez de irla enviando a medida que se va generando. Hay que pasarle el parámetro de texto ob_gzhandler para que al final comprima todo lo que tiene en el buffer antes de enviarlo. Finalmente ponemos ob_end_flush al final del todo de la página php, que sirve para cerrar el buffer y enviarlo todo.

Y para terminar, solo deciros que lo useis, ya que os supondrá un ahorro bastante efectivo. Si quereis comprobar si lo teneis instalado en vuestro servidor, buscad las librerias zlib, zend y la variable output_buffering a 1 en un phpinfo.

Detección de movimiento con una webcam

En este proyecto mi intención no es otra que hacer un sistema de detección de movimiento (que no de reconocimiento de objetos).

Detectar movimiento no es una cosa sencilla como pueda parecer a priori, ya que la imágen que pueda dar una camara (en este caso un webcam) no es de una calidad suficiente como para que dos imágenes tomadas en distintos momentos puedan considerarse iguales. Esto es debido a que las cámaras suelen introducir ruido en las imágenes que captan, o dicho de otra forma, un pixel de una posición determinada de la imágen nº1 no suele coincidir casi nunca (por no decir nunca) con un pixel de la misma posición de la imágen nº2 (aún siendo estas tomadas con una diferencia de milisegundos). Es por ello que hay que pensar que nivel de tolerancia hay que permitir para que aunque las imágenes no sean iguales exactamente, la información que contienen si sea similar en gran medida; sin detrimentro por supuesto de que si hay algún movimiento de un objeto o de un ser vivo sea tomado como informaciones distintas y provoque un evento o acción.

Existen varias formas de trabajar con esta tolerancia: algoritmos de detección de bordes (gradientes, derivadas gausianas, transformada de Hough, etc), filtrados descriptores de Fourier, clasificador Bayesiano, etc), etc. Todos ellos sirven, pero no son iguales de rápidos. Es por ello que me decanté por el metodo estadístico de hacer medias de pixeles con los de su alrededor, un metodo sencillo para fijar una tolerancia en escaso tiempo (aunque quizá con un poco de penalización en cuanto a acierto en detección).

El método consiste en tomar cada pixel de la imágen nº1 y sumar su valor con los 8 pixeles que le rodean (una matriz de 3×3) y luego dividir el resultado por 9, por lo que nos da un valor medio. El mismo proceso lo hacemos con los mismo pixeles pero de la segunda imágen, y así obtenemos otro valor medio. Al compararlos podemos detectar cuanto % de diferencia hay entre uno y otro, momento por el cual, gracias a que hemos configurado que nivel de sensibilidad en la diferencia, o se admite como que no es un valor a tomar en cuenta, o sin embargo el valor es distinto y por lo tanto se toma en cuenta. Si se sobrepasa una cantidad determinada de pixeles que se toman en cuenta (sensibilidad por puntos), entónces es que las imágenes no son completamente iguales en cuanto a información y se supone que se ha producido un movimiento (cambio de posicion de entidades en la imágen o aparación de otras nuevas). La idea es que se tome una imágen de referencia (una del entorno estático), y se comparen las restantes con ella, para poder así saber con respecto al origen si ha habido algún cambio. Más tarde se toma otra imagen de referencia eliminando así los problemas que pudieran causar otros agentes (como un cambio atenuado de luz por el sol).

Media de pixeles

Siguiendo esta idea, he desarrollado una aplicación en visual c++ 6.0 llamada DETECTOR donde he aplicado los conceptos anteriormente citados. Podeis descargar el ejecutable y/o su código fuente en esta dirección (esta bajo licencia creative commons): https://www.sistemasorp.es/detemovi

Otro sistema más para combatir el antispam

Hace ya tiempo que le estuve dando vueltas a como combatir el spam de una vez por todas…

Es de sobra conocido que los filtros anti-spam tienen dos defectos, por un lado filtran muchas veces correos spam como legítimos, y viceversa, correos que estamos esperando no los recibimos porque el filtro los considera spam.

La solución de tener listas negras de ips (los dominios no sirven porque los spammers pueden poner el que quieran como remitente) no es en absoluto fiable, ya que por ejemplo un usuario puede enviar spam desde una linea adsl (ya sea conscientemente o sin saber que esta infectado por un troyando o virus) y al ser ip dinámica, otro usuario que la tome posteriormente no podrá enviar emails; o aún peor, meter a todo un rango de ips en una lista negra (como pasó con telefonica) y fastidiando a todos los usuarios de ese ISP que quieran enviar emails.

El sistema que hace google (y desarrollado por yahoo) de firmar los emails esta bién, pero aún no esta implantado masivamente y tardará aún mucho que todos los programas servidores y clientes de SMTP lo implanten (y peor aún cuando Microsoft no lo tome como estandar y se invente el suyo propio).

Mi solución, a falta de cubrir ciertos aspectos técnicos se presenta en el siguiente diagrama:

Básicamente consiste en pedir confirmación de los emails a su remitente antes de tomarlos como buenos en futuras ocasiones. Faltarían detalles como listas de correos o publicidad requerida, pero este sistema funcionaría con la tecnología actual y funcionaría como puente entre el servidor POP3 y el cliente de correo.

¿Buscas un código fuente?

Pues en www.koders.com seguramente encuentres algo parecido a lo que estés buscando. Se trata de un buscador de código fuente donde como criterios de busqueda puedes filtrar por lenguaje de programación o licencia de uso del mismo. La única pega es que para encontrar lo que andabas buscando tengas que leer un chorro de codigo de otra persona que tenga una forma curiosa (horrible) de hacer las cosas, cosa por la cual ya he tenido que pasar en algún que otro trabajo donde he estado :).

Configurar Linux como Router

Recientemente he adquirido un ordenador de 2º mano en mi empresa. La utilidad que le voy a dar es la de tener un ordenador en la casa donde voy de veraneo en Cercedilla. Pero claro, durante estos días lo he estado configurando y metiendole todos los programas necesarios y los que preveía que tarde o temprano usaré. Con este ya suman 4 los ordenadores que tengo, a saber:

Servidor: VIA EPIA 800, 128 MB RAM, linux

Uso diario: AMD XP, 2.4 Ghz., 512 MB RAM, 280 GB HD, linux, windows xp

Portatil: AMD XP Mobile, 2.4 Ghz, 512 MB RAM, 40 GB HD, windows xp

Nueva adquisición: Pentium IV 2.4 Ghz, 768 MB RAM, 20 GB HD, windows xp

Pues con estos equipos el otro día se me ocurrió hacer dos redes, una del tipo 192.168.0.0/24 y otra del tipo 10.0.0.0/8 que estuviesen unidas al nuevo equipo, actuando este como router. En la red 192* tenía el ordenador de uso diario y el router ADSL, y en la red 10* tenía al portatil. Mi intención era que todos los ordenadores se vieran entre si y también tuviesen acceso a Internet. El ordenador nuevo tenía dos tarjetas y corría el linux knoppix. Una tarjeta tenía la ip 10.0.0.254 y la otra tenía la ip 192.168.0.4. En linux ambas se configuran así a través de la shell o linea de comandos:

ifconfig eth0 192.168.0.4 netmask 255.255.255.0 up

ifconfig eth1 10.0.0.254 netmask 255.0.0.0 up

En este ordenador, la puerta de enlace o gateway estaba configurado para 192.168.0.254, o lo que es lo mismo, la ip que tiene mi router ADSL:

route add default gw 192.168.0.254

El portatil y el ordenador de uso diario ejecutaban windows xp y tenian como ip 10.0.0.1 y 192.168.0.1 respectivamente. El portatil estaba conectado a un switch (con puerta de enlace 10.0.0.254) al igual que una de las tarjetas del ordenador nuevo; el ordenador de uso diario estaba conectado al router ADSL (como es un hub al fin y al cabo; con puerta de enlace 192.168.0.254) al igual que la otra tarjeta del ordenador nuevo.

Una vez ya todo conectado puse en el linux del ordenador nuevo esta sentencia desde la shell:

echo «1» > /proc/sys/net/ipv4/ip_forwarding

que permitia reenviar los paquetes tcp/ip por las redes que tenia acceso este ordenador (se puede ver poniendo un simple route en linux)

Pero hay triste de mi que los ordenadores host no se veian entre ellos, ya que haciendo ping de uno a otro no se veian, sin embargo si veian al ordenador nuevo, aunque curiosamente si veían al router y también podían navegar por Internet (en ambos estaban puestas ya las DNS correctas), por lo que pensé que algo había hecho mal. Asi que pensando, pensando, cambié la puerta de enlace del ordenador de uso diario que estaba como he comentado antes a 192.168.0.254 a 192.168.0.4 y ¡¡¡ voila !!! ya se veían entre ellos. Había creado dos redes con casi nada de esfuerzo. Luego ya me entretuve con el iptables para configurar accesos desde el shell como:

iptables -A FORWARDING -p tcp –destination-port 80 -j DROP

que no permite el paso de paquetes por el puerto http o

iptables -A FORWARDING -s 192.168.0.0/24 -d 10.0.0.0/8 -j DROP

que no permite el flujo de daots entre una red y otra.

El dibujo de la red sería tal que así:

y muestra como aunque el ordenador de uso diario y el router ADSL estan en la misma red, los paquetes entre uno y otro deben pasar por el ordenador nuevo.

Transparencias con Windows y GDI en Visual Basic

En el trabajo me surgió la problematica de hacer que una imágen tenga un grado de transparencia sobre otra. Esto, aunque parezca una trivialidad, no lo es puesto que aunque la solución original es generar una mascara para hacer la transparencia, el permitir que existan varios grados lo complica un poco. Sin embargo al final he conseguido compactarlo todo en un procedimiento para que pasandole como parametros el dispositivo de contexto de origen, el dispositivo de contexto de destino (y donde se almacenará el resultado de la transparencia), las dimensiones de la imagen (en mi caso suelo poner las dimensiones en pixeles del picturebox) y el grado porcentual de transparencia, se genera de un modo casi inmediato el efecto deseado. Aqui os dejo el código:

Actualización 07/07/2005:
El código de aquí arríba es más limitado de lo que yo pensaba y hace cosas que no debiera, por lo que hoy que hemos estado probandolo lo hemos descartado y en su lugar he encontrado algo mucho más sencillo… La función AlphaBlend de la API de windows 98, Me, 2000 y XP:

Primero colocais en la variable número un valor entre 0 (transparente) y 255 (opaco) para definir el nivel de transparencia de la imagen origen con respecto a la de destino, posteriormente con una sencilla formula (no os calenteis mucho la cabeza, ya que es una regla nemotécnica para darle un valor) se saca el valor a pasar al último parámetro de la función. Luego ya en la función le pasais el hdc de destino, el punto x e y del empiece a trabajar del destino y el ancho y alto del destino, posteriormente los mismos parámetros pero esta vez los del origen.

Funciona bastante bién y estará en todos los windows modernos.