lunes, 26 de noviembre de 2018

(1/2) Hotspot con portal captivo y autoregistro( VirtualBox,FreeRadius, Coovachilli, HostAPd, MySQL,wifi USB)




CentOS7: (1/2) Hotspot con portal captivo usando  VirtualBox, Wifi USB , FreeRadius, Coovachilli, HostAPd, MySQL y auto-registro.


Situación Presentada


Ya hace tiempo un amigo puso una tienda de café y pues como todo local pequeño maneja su wifi sin aislarla de su red local, lo cual presentaba muchos problemas, sobretodo al momento de su facturación que requería el internet (por lo de los POS para tarjetas), y también el riesgo de que alguien se ponga a tocar más de lo que debe en la red.
También mi amigo deseaba algo parecido a lo que tienen restaurantes en los que recaban correo electrónico y otros datos.

Y qué hago entonces?

Para reducirle los costos al mínimo a mi amigo, y de paso hacer gala de lo que se puede hacer usando open source , algo de tiempo  y dedicación, le dije que íbamos a usar su PC de Caja con un Linux virtualizado, que solo comprara el adaptador Wifi USB, que funciona en modo AP.

Entrando más a detalle lo que se hará es convertir la computadora de escritorio disponible en un hotspot inalambrico donde los clientes se podrán autenticar usando una pagina del portal captivo.

Se va a usar una pieza de software llamado Hostapd para crear el access point con el USB wifi, se va a instalar Freeradius para autenticar en red, CoovaChilli para montar el DHCP y redireccionar al portal captivo.

Componentes del articulo

El contenido se parte en dos debido al limite que da Blogger por post.

 Parte 1
1.Pre-requisitos para instalación
2.Configuración Virtualbox
3.Freeradius, autenticacion para clientes en red
4.Hostapd, Access Point con USB Wifi
5.Modificar intensidad de señal (dBm)

 Parte 2 (ir)
6.CoovaChilli, portal captivo y DHCP.
7.Probar portal captivo
8.Administración de usuarios
9.Autoregistro y otras personalizaciones del portal


1. Pre-requisitos para instalación

  • Una computadora que pueda virtualizar por lo menos con 10GB libres y 1GB RAM.
  • Un adaptador USB,  en este caso se usó una TP-Link WN7200nd (chipset rt3070/rt2800) también funciona con otras como la WN722n (chipset rtl8188eus) pero deben actualizar el kernel del Linux a 4.4+.
Si no se usan estos dos, usar cualquiera que soporte modo AP,  se puede verificar esto usando el siguiente comando:

sudo iw phy | grep  -A4 -i 'Supported interface modes'
  • Un Linux, en este articulo estaré usando CentOS 7, deben tener el repositorio instalado tambien.

   yum install epel-release

  • Todos los paquetes que vamos a instalar (y librerias de desarrollo a veces, todo esta aquí)
  • Una instancia de MariaDB (o mysql), si no la tienen instalenla, el default pass para root está en blanco.    
   yum install mariadb-server mariadb
  • Una conexión de red a internet (cableada preferiblemente)
  • Conocimiento intermedio de manejo del shell en Linux, Virtualbox y MariaDB (MySQL) ,  

2. Configuración Virtualbox (para detectar USB Wifi)

Como mencioné en los pre-requisitos, ya deberían saber como montar una VM en esta herramienta de Oracle, así que solo explicaré qué hay que hacer para que mapee la USB Wifi a tu VM como que estuviera conectada directamente.
Eso se hace en las opciones de la maquina (settings), luego en el apartado USB , y finalmente le dan click (con la VM apagada) en el plug/conector USB con el signo +  y les aparecerá el dispositivo, y luego le dan OK

**NOTA: Para que la VM lo detecte, tendrán que desconectar el USB, con el filtro USB ya creado,  encenderla y una vez dentro , conectar el USB y lo encontraran.

Para confirmar que si detectó el dispositivo, pueden correr el siguiente comando que mostrará los dispositivos USB conectados, y deberá aparecer el que agregamos al filtro USB.

lsusb

3.       Freeradius


Freeradius es un servidor de Raiuds open source, está disponible para todas las distribuciones,
sirve para autenticar los clientes antes que salgan a internet.

Se necesitan instalar tanto el servidor como el plugin para mysql

yum install freeradius freeradius-mysql freeradius-utils -y

Configurar Freeradius
MariaDB debe estar corriendo, como mencione en los pre-requisitos ya deben tener conocimientos de eso para llevarlo a cabo.

-Crear la base de datos para radius:
echo “create database radius” | mysql -u [usuario_mysql] -p[password_mysql] 

-Generar tablas
en la bd de radius con el esquema que ya trae el plugin de radius:
mysql -uroot  -p radius < /etc/raddb/mods-config/sql/main/mysql/schema.sql

Crear usuario mysql para  los privilegios en la bd radius, dentro de mysql:
GRANT ALL PRIVILEGES ON radius.* to ‘usuariodb_radius’@’localhost’ IDENTIFIED by 'usuariodb_radius_password';

-Configurar modulo sql de Radius:
**Nota: Pueden usar nano o Emacs si no les gusta vim

sudo vim /etc/raddb/mods-available/sql


Descomentar o cambiar los siguientes valores:
driver = "rlm_sql_mysql"
dialect = ”mysql”
server = "localhost"
port = 3306
login = "”usuariodb_radius"
password = "usuariodb_radius_password"
read_clients = yes

-Contadores sql para chillispot :
sudo vim /etc/raddb/mods-available/sqlcounter

agregar al final del archivo :

$INCLUDE ${modconfdir}/sql/counter/${modules.sql.dialect}/chillispot.conf

-Agregar los link simbolicos para el modulo sqlcounter:
sudo ln -s /etc/raddb/mods-available/sql /etc/raddb/mods-enabled/sql
sudo ln -s /etc/raddb/mods-available/sqlcounter /etc/raddb/mods-enabled/sqlcounter

-Configurar servidor radius:
sudo vim /etc/raddb/radiusd.conf

Bajo la sección seguridad, cambiar el usuario y gripo creados durante la instalación:
user = radiusd
group = radiusd
allow_vulnerable_openssl = yes

**Nota:  No hacer esto realmente en producción, lo mejor es actualizar la versión del openSSL

Bajo la sección “ instantiate “ por la linea 728, agregar los siguientes modulos de contador:
chillispot_max_bytes
noresetcounter

-Configurar el servidor virtual default en sites-available:
sudo vim /etc/raddb/sites-available/default
Bajo la sección “ authorize “:
Comentar lo siguiente:
#filter_username
Des-comentar lo siguiente:
auth_log
unix
Cambiar lo siguiente:
'-sql' a sql
Agregar lo siguiente al final de la sección “ authorize “ por la línea 273:
chillispot_max_bytes
noresetcounter

Bajo la sección ” accounting “, descomentar:
radutmp
Cambiar:
'-sql' a sql

Bajo la sección ” session “ , descomentar:
radutmp
sql

Bajo la sección ” post-auth  “, descomentar:
reply_log
Cambiar lo siguiente:
'-sql' a sql

-Configurar las solicitudes del servidor virtual para el  inner tunnel:

sudo vim /etc/raddb/sites-available/inner-tunnel


Bajo la sección ” authorize “, cambiar:
'-sql' a sql
Agregar lo siguiente al final de la seccion “ authorize “:
chillispot_max_bytes
noresetcounter

Bajo la sección ” session “, descomentar:
sql

Bajo la sección ” post-auth “, descomentar:
reply_log
Cambiar:
'-sql' a sql

-Configurar clients del radius
sudo vim /etc/raddb/clients.conf
Poner el password usado para acceder a verificación de clientes a la base de datos de FreeRadius (mínimo 8 caracteres):
secret = probando123

-Agregar los siguientes contadores para Chillispot:
sudo vim /etc/raddb/mods-config/sql/counter/mysql/chillispot.conf


sqlcounter chillispot_max_bytes {
counter_name = Max-Total-Octets
check_name = ChilliSpot-Max-Total-Octets
reply_name = ChilliSpot-Max-Total-Octets
reply_message = "You have reached your bandwidth limit"
sql_module_instance = sql
key = User-Name
reset = never
query = "SELECT IFNULL((SUM(AcctInputOctets + AcctOutputOctets)),0) FROM radacct WHERE username = '%{${key}}' AND UNIX_TIMESTAMP(AcctStartTime) + AcctSessionTime > '%%b'"
}

-Cambiar permisos de logs y archivos de configuración:
sudo touch /var/log/radius/radutmp
sudo chown -R radiusd:radiusd /etc/raddb
sudo chown -R radiusd:radiusd /var/log/radius

-Crear usuario Admin de Radius en db de mariadb:
mysql -u usuariodb_radius -p -e "INSERT INTO radius.radcheck (UserName, Attribute, Op,Value) VALUES ('usuario_admin', 'Cleartext-Password', ':=', 'password_admin');"

Deberia quedar algo así :
**Nota: Nota que el valor del password debe ser fuerte, no de diccionario.
-Iniciar Radius para realizar prueba
sudo systemctl start radiusd
Abrir nueva terminal y ejecutar lo siguiente:
radtest usuario_admin password_admin 127.0.0.1 1645 probando123

Tendria que salir algo así, y al final recibir un mensaje Access-Accept:

 



4. Hostapd

hostapd es un excelente software que permite convertir un Linux en un punto de acceso wifi (AP) WPA/WPA2 totalmente configurable
Para instalarlo, ejecutar

yum install hostapd -y

Para verificar que fue instalado ejecutar:

hostapd -v

-Configurar hostapd
Abrir archivo de configuración:

sudo vim /etc/hostapd/hostapd.conf

Cambiar lo siguiente en este archivo:
driver=nl80211 # el driver interface entre las operaciones wifi y el kernel
interface=wlan0 # cambiar este a tu dispositivo wifi (ver con comando
ip a )
ssid=MiRedPlecaEtece # cambiar para que sea tu SSID
hw_mode=g # modo de wireless
channel=6 # canal
ieee80211n=1 # habilita el Wireless N
wpa=1
wpa_passphrase=password_wpa
wpa_pairwise=TKIP CCMP
rsn_pairwise=CCMP

o si quieren con la red abierta, para utilizar la autenticación Radius (portal) únicamente, cambiar
wpa=0

 -Iniciar y probar hostapd:
Hay que poner el estado del cliente Wifi  en off, y luego quitar el modo avión(desbloquearlo):

sudo nmcli radio wifi off

sudo rfkill unblock wifi

Iniciar servicio

sudo systemctl start hostapd

Si todo esta bien, debería iniciar el servicio y con cualquier dispositivo deberían ver la red disponible CON los parámetros que le dimos (tipo de red, contraseña, si es abierta, etc)




5. Modificar intensidad de wifi (dBm)


Para esto, primero debemos identificar cuanto es el máximo que soporta en dBm nuestra tarjeta wifi, ejecutando este comando.

sudo iw list | grep dBm
Nos muestra que para todos los canales disponibes, el máximo son 20 dBm.
 
-Cambiar potencia de transmisión.
Esto se hace en unidades mBm , donde cada 1dBm = 100 mBm,  es decir
20 dBm = 2000 mBm máximo, y el mínimo pues, hay que ir probando hasta encontrarlo.
En el caso de la USB wifi usada para este articulo, lo mínimo son 900 mBm ó 9dBm, que equivale como a 5 metros a la redonda.

sudo iw dev wlp0s6u1 set txpower limit 900

domingo, 4 de marzo de 2018

ESXi: Instalar VMWare VSphere (BareMetal) 6.5 en Desktop con driver personalizado (NIC no Intel)

Instalación ESXi 6.5 en ordenador salvaje y corriente con una    TPLink TG-3269 (Realtek 8168) 1Gbps

De entrada les comento que VMWare regala una licencia si es uso personal, he allí porque el post.

Problema Presentado

Al tratar de instalar VMWare ESXi 6.5 en tu ordenador, recibes un mensaje que la instalación no poder terminar porque el adaptador de red no se encuentra!! 😢
Pero si está instalado, hasta me compré una tarjeta de red de 1Gbps y desactive la interna desde el BIOS, ¿Cómo puede ser?.
Bueno, VMWare no tiene soporte para todos los drivers, usualmente los Intel son inmediatamente detectados, pero otros considerados third party, debemos agregarlos manualmente


Y que hago entonces?

La solución inmediata es poner los drivers del chipset(en este caso RTL8168 usada por TPLink TG-3269).

Guía de instalación rápida antes de personalizar la ISO de VMWare VSphere 6.5:

Cómo Bonus creo que es ideal explicar como bajar la ISO de ESXi con licencia para home use:

** Tienes que crear una cuenta o te haces login si ya lo tienes
Después de haberte registrado te darán una license key, y acceso a los binarios.

  • Descargar el Hipervisor de VMWare vSphere 6.5

  • Instálalo en tu PC, desde la USB con Rufus podes crear la imagen booteable.

Si no tienes una NIC Intel 1Gbps mínimo, esto hazlo hasta luego de crear tu imagen personalizada.


Identificar el chipset de la NIC (tarjeta de red) si NO te dejar instalarlo.

Cuando aparezca el mensaje de error

En vez de presionar enter, presione [Alt] y [F1] en el teclado , y aparecerá una pantalla de login en el shell de ESXi, donde entraremos con root, sin contraseña. Luego corremos el commando para listar los dispositivos PCI y le hacemos un pipe para encontrar lo que necesitamos:

lspci -v | grep “Class 0200″ -B 1
**Disculpas por la calidad, es foto de celular .

Descargar paquete de drivers (archivo .zip) que soporten este chipset (Realtek 8168)

En https://vibsdepot.v-front.de/wiki/index.php/List_of_currently_available_ESXi_packages  encontraran third party NIC drivers variados para ESXi .

En mi caso me bajo el zip para el RTL8168

Ya tenemos preparado los drivers y toca utilizar el ImageBuilder para crear la nueva ISO que los contendrá.

Instalar PowerCLI para VMWare ImageBuilder

Esto se hace con PowerShell, en mi caso estoy usando:
PowerShell:  v5.1
OS: Windows 10 Home

Ejecutar los siguientes comandos en tu shell:

Save-Module -Name VMware.PowerCLI -Path "t:u\ruta\destino"
 Install-Module -Name VMware.PowerCLI

Trabajando perfiles de imagenes con el PowerCLI VMWare.ImageBuilder 

En powershell primero hay que quitarle la protección de ejecución de scripts
Set-ExecutionPolicy RemoteSigned
**Aquí elegir [ Y ] si queremos solo por esta sesión, [ A ]para todos los casos de ahora en adelante

Agregamos el depósito de imágenes de perfil
Add-EsxSoftwareDepot https://hostupdate.vmware.com/software/VUM/TEST/main/vmw-depot-index.xml, E:\Dev2017\ESXi\customdrivers\net55-r8168-8.045-napi-offline_bundle.zip
Buscamos la imagen standard de ESXi
Get-EsxImageProfile -name "ESXi-6.5*"

Agregando el driver que necesitamos
Add-EsxSoftwareDepot E:\Dev2017\ESXi\customdrivers\net55-r8168-8.045-napi-offline_bundle.zip
    **Nota: Esta ruta "E;\Dev2017....." es de mi PC, la ruta de ustedes debe ser alguna personalizada, igual deben cambiarla en el powershell.

Clonamos la imagen standard (ESXi-6.5) para trabajar con ella, y le metemos los drivers "sin que se cuenta."
New-EsxImageProfile -CloneProfile "ESXi-6.5.0-4564106-standard" -name "ESXi-6.5.0-4564106-standard-con-RTL8168" -vendor "DriverTPLinkTG3269"

Exportamos a la nueva ISO la imagen con los drivers.
Export-ESXImageProfile -ImageProfile "ESXi-6.5.0-4564106-standard-con-RTL8168" -ExportToISO -filepath E:\Dev2017\ESXi\customdrivers\ESXi-6.5.0-4564106-standard-con-RTL8168.iso

Otro Metodo (en caso de error de "Time-Out" u otro en paso anterior)

En caso que no funcione con el método ISO, por algún error de time-out.
Deberemos exportar el Paquete (bundle) como .zip localmente
Export-ESXImageProfile -ImageProfile "ESXi-6.5.0-4564106-standard-con-RTL8168" -ExportToBundle -filepath E:\Dev2017\ESXi\customdrivers\ESXi-6.5.0-4564106-standard-con-RTL8168.zip
Luego agregar esta ruta con la imagen nueva como ESXSoftwareDepot :
Add-EsxSoftwareDepot E:\Dev2017\ESXi\customdrivers\ESXi-6.5.0-4564106-standard-con-RTL8168.zip,  E:\Dev2017\ESXi\customdrivers\net51-r8169-6.011.00-2vft.510.0.0.799733-offline_bundle.
zip

Cambiamos el nivel de aceptación de la Imagen a CommunitySupported, y agregamos el paquete de driver
Set-EsxImageProfile -Name "ESXi-6.5.0-4564106-standard-con-RTL8169-latest" -AcceptanceLevel CommunitySupported
Add-EsxSoftwarePackage -ImageProfile "ESXi-6.5.0-4564106-standard-con-RTL8169-latest" -SoftwarePackage net51-r8169



Y ultimo exportamos la ISO con el mismo comando que ejecutamos anteriormente:
Export-ESXImageProfile -ImageProfile "ESXi-6.5.0-4564106-standard-con-RTL8169-latest" -ExportToISO -filepath E:\Dev2017\ESXi\customdrivers\ESXi-6.5.0-4564106-standard-con-RTL8169-latest.iso
**Recordar: Que la ISO se está creando con el Bundle ZIP que descargamos de la imagen que ya habíamos preparado antes con los drivers RTL8168 y RTL8169 , y que se hizo de esta forma debido a un posible error de TimeOut que nos envía VMWare o cualquier otro error.



Y ahora solo hace falta cargar la ISO al USB con Rufus, e instalar con tus drivers de la tarjeta TPLink.

Al final lo que buscamos es esta bella pantalla

Y de aquí seguir con la instalación standard.

Referencias

Get ESXi 6.5 with license
http://www.virten.net/2016/11/free-esxi-6-5-how-to-download-and-get-license-keys/
Add ESXi Depot
http://www.vmdaemon.com/2014/10/powercli-imagebuilder-problem_solved/
Add NIC driver
https://akhpark.wordpress.com/2017/01/19/enable-realtek-nic-on-vmware-vsphere-6-5/
Adding the async driver to the ESXi installation ISO bundle in ESXi (2137851)
https://kb.vmware.com/s/article/2137851
Set up home lab
http://www.ryanbirk.com/the-perfect-vsphere-6-home-lab/

jueves, 25 de enero de 2018

BASH - Función para revisar listado de IP con ping

Hace tiempo me tocaba administrar multiples servers RedHat5 en producción, los suficientes para exigir un delay minimo en un full deployment de clases, instrucciones o actualizaciones a las aplicaciones que alojaban.

Para realizarlo, se hacia mediante un Script en BASH que estaba centralizado en un backend que todos podian ver, y con el que se logueaban por llave públicas (Autenticacion SSH por llave publica RSA) .

Los siguientes problemas se generaban:
- Algunos servidores estaban fuera de linea o no estaban accesibles.
- No habia log o notificacion de los fallidos.
- Se perdía la posibilidad de hacer un redeploy o rollback en caso de error.

Se resuelven estos puntos, creando una función para verificación de conexión.
*Nota: Esto solo aplica para el caso de conectividad, actividades propias del deploy deben tener su propio fail-safe.

Con que vamos a trabajar:

  • Manipulación de STDOUT ( Pipes )
  • BASH ( Arreglos, Ciclos)
  • gAWK (Substring, FNR, var, print )  

La función trabajará con un arreglo que ya contiene las direcciones IP, pero por motivos de practica, vamos a llenarlo con un archivo de texto

Desarrollo de funciónes:
Esta función se puede colocar en cualquier parte del script que se necesite.
Se irá comentando el código ( # ) para que pueda hacerse un copiar y pegar.

[usermacizo@centos ~]# vim tuscript.sh
  ó
[usermacizo@centos ~]# nano tuscript.sh

#-- Inicio del codigo

#!/bin/bash
## Este es un carrier que porta mis saltos de linea cuando no puedo poner un \n normal, por ejemplo se ve en los read -p .

cr=$(echo $'\n.')
cr=${cr%.}

## Se inicializa cuentaIP que será la variable que se usará para guardar el conteo de las IP que se van a evaluar, ya sea que vengan de un archivo de texto, que sean ingresadas manualmente, o de un rango especifico (en este caso solo usaremos archivo de texto)

cuentaIP=0

##### Se carga el arreglo con direcciones IP desde archivo de texto #####

archivo="/home/usermacizo/listado_ip.txt"

 while read -r linea || [[ -n "$linea" ]]; 
      do
       cuentaIP=$(( $cuentaIP + 1 ))
       direcciones[cuentaIP]=$linea  
      done < "$archivo"

# -r evita que secuencias de escape se interpreten (\ contrapleca)
# || [[ -n $linea ]]  evita que la última línea se ignore ya que esta es un EOF y no termina con \n.


##### Función para revisar IP que están en línea #####

revisarOnline()
{

# estas son las vars que llevaran el conteo de los servidores en linea y offline.  
 CuentaOn=0
 CuentaOff=0

 echo "*** Verificando de Conexion de ***"

#Se empieza en 1 y no en cero por cuestiones de estetica al momento de enumerar el resultado, igualmente cuando se cargan las IP al arreglo se comienza desde 1.

for (( cC=1;cC<=$cuentaIP;cC++))
do
 if [ "${direcciones[cC]}" != "" ]
 then


#El truco para determinar si está en línea o no, se encuentra en la siguiente línea, que evaluará todos las direcciones IP en el arreglo, a continuación lo explico a detalle:
##  se le hace un ping a la IP actual del arreglo con los argumentos -c 1 (contar una sola vez) y -w 2 (esperar solo 2segs hasta timeout)
## enviamos por un pipe lo que estos nos arroja al gAWK ,  donde seleccionamos la segunda linea de las lineas con el FNR==2 (number of record) y le ordenamos que imprima el substring del primer caracter, de la columna 6 
# Hecho todo esto, si hay un Ping nos va a responder, algo así:
#         PING 192.168.7.1 (192.168.7.1) 56(84) bytes of data.
#        64 bytes from 192.168.7.1: icmp_seq=1 ttl=64 time=2.08 ms
# Por eso es que con el gAWK, extraemos de la segunda línea, y le columna #6 el valor, que sería "ttl", pero usado el substring, nos daría unicamente "t"

    esTTL=$(ping ${direcciones[cC]} -c 1 -w 2 | gawk '(FNR==2) {print substr($6,1,1)}')

    if [[ $esTTL == "t" ]]
    then
# se incrementa el contador online, y se mete al arreglo la direccion. 
     cuentaOn=$(( $cuentaOn + 1 ))
     servidoresOn[cuentaOn]=${direcciones[cC]}
    else
# se incrementa el contador offline, y se mete al arreglo la direccion.
     cuentaOff=$(( $cuentaOff + 1 ))
     servidoresOff[cuentaOff]=${direcciones[cC]}
    fi

  fi
done

# Impresión de los resultados en pantalla

echo "---------------------------"
echo "Cantidad Online: $cuentaOn "
echo "------ Listado -------"
printf '%s\n' "${servidoresOn[@]}"

echo "---------------------------"
echo "Cantidad Offline: $cuentaOff "
echo "------ Listado -------"
printf '%s\n' "${servidoresOff[@]}"

# Notar que para el listado de IP no se uso echo, sinto el printf, con un caracter de escape \n para cada nuevo elemento, esto para que no aparezca en una sola linea horizontal.

}

revisarOnline

#-- Final del codigo