SEMS en EdgeRouter’s como SBC

Muy buenas a tod@s de nuevo!

Esta vez seguimos la senda VoIP, con una parada en uno de los elementos que consideramos imprescindible de un tiempo a esta parte y del cual todavía no habíamos hablado: SEMS.

¿SEMS?

De sus siglas sacamos : SIP EXPRESS MEDIA SERVER. Este proyecto salió del mismo sitio que el gran OpenSER (más tarde luego Kamailio / OpenSIPS), del Fraunhofer FOKUS (German public R&D institute).

Para explicar más en detalle, creemos que son de obligada referencia estas diapositivas de Stefan Sayer (Chief Technology Officer, Co-Founder at FRAFOS GmbH)  presentadas en el Kamailio World 2014

Nos permitimos coger una imagen de su presentación para ilustrar los casos de uso principales:

Para el caso que nos ocupa en este post, hablaremos de las funciones SBC que nos da SEMS, que principalmente:

  • Facilidad de configuración, sin necesidad de entrar en complicaciones tipo DSM.
  • Muy estable.
  • Rendimiento «natural» muy alto (veremos luego).

Lo que es recientemente, la compañia FRAFOS (desde Aprox 2010) cogió el desarrollo de SEMS, y lo utilizan en su producto comercial FRAFOS ABC SBC, donde trabajaba nuestro querido antiguo compañero Jose Luis Millán, conocido por algunos como «el intenso» 😉 jjijiji

SBC como concepto

Si buscamos por SBC, prácticamente todos los fabricantes importantes tienen el suyo propio, si buscamos la definición, eso ya no lo tenemos tan fácil.

De hecho, esta cita del RFC5853 (Requirements from Session Initiation Protocol (SIP) – Session Border Control (SBC) Deployments) es francamente ilustrativa:

2. Background on SBCs

The term SBC is relatively non-specific, since it is not standardized
or defined anywhere.

Incluso Olle E. Johansson nos comentaba en persona más de una vez que es un término puramente comercial, pero en lo que si estaremos muchos de acuerdo es en su necesidad, lo llamemos como lo llamemos 😉

Bajo nuestra perspectiva, ni siquiera hay que tirar del argumento de redes VoIP grandes con muchos fabricantes/integradores diferentes, donde es fácil verle la necesidad. Si nos centramos incluso en los casos sencillos, también nos aportan mucho – a un coste tanto económico como técnico razonable. La pega principal es que rompen el concepto de SIP2SIP with END2END full transparency.

Desde funciones como topology hiding, protocol adapter, «SIP Mediator», hasta otras ya quizás más puras de un proxy (routing), son las habituales atribuibles a este tipo de elementos.

Por resumirlo al extremo, al igual que muchas corporaciones tienden a concentrar sus salidas WAN detrás de un cluster de firewalls, que no sólo son L7 aware, sino que son full DPI, en SIP suele suceder lo mismo: concentrar toda integración de flujos SIP en este elemento/cluster de elementos, para tenerlo todo localizado en un único punto, a todos los efectos.

En nuestro caso, para lo que es este post en sí (obviamente, no para todos los casos), nos queremos centrar más en el concepto de sip network entry point, es decir considerarlo un elemento de acceso a la red, pero considerarlo de forma general, no pensar en tener un único SBC, sino todo lo contrario. Sirva este esquema para ilustrar este caso de uso:

Por así decirlo: si necesitamos un router (porque vamos contra un servicio mayorista tipo NEBA o similar, porque queremos tener gestión, porque nos hace falta o simplemente porque queremos): ¿Por qué no darle funciones ya de SBC + Punto de captura con el kit increíble: CAPTAGENT + HOMER SIP CAPTURE ?

Con esto lo que ganamos es visibilidad total, capturar no sólo lo que nos llega, sino lo que está realmente saliendo, con lo que cualquier culebrón habitual con SIP ALG se convierte más bien en un abrir y cerrar de ojos.

¿EdgeRouter?

La verdad es que de EdgeRouter’s hemos hablado bastante por este blog, de hecho, lo que es en Irontec, los hemos puesto realmente como churros, sin exagerar, muchísimos. Cuando los vimos, parecía que alguien se había hecho eco de nuestros deseos en este mundo IT:

  • Basado en Debian GNU/Linux
  • Precio realmente muy económico.
  • Muy muy muy orientado al networking – una de nuestras pasiones (con EdgeOS / Vyatta)
  • Pero en general muy personalizable, y de forma standard, sin aventuras tipo OpenWRT ni nada similar, todo totalmente oficial y mantenido por Ubiquiti.

La versión concreta de la distro depende del modelo, en nuestro caso el modelo con el que queremos ilustrar este post es el EdgeRouter Lite:

En lo que respecta este modelo: Debian Wheezy (7.X), 512Mb de RAM, dual core MIPS (Cavium Octeon+) y aprox 1.5Gb de espacio libre utilizable para paquetes propios:

ubnt@ubnt:~$ cat /etc/debian_version
7.11

ubnt@ubnt:~$ df -h /
Filesystem                Size      Used Available Use% Mounted on
unionfs                   1.6G    171.6M      1.4G  11% /

ubnt@ubnt:~$ cat /proc/cpuinfo
system type		: UBNT_E100
machine			: Unknown
processor		: 0
cpu model		: Cavium Octeon+ V0.1
BogoMIPS		: 1000.00
wait instruction	: yes
microsecond timers	: yes
tlb_entries		: 64
extra interrupt vector	: yes
hardware watchpoint	: yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb]
isa			: mips1 mips2 mips3 mips4 mips5 mips64r2
ASEs implemented	:
shadow register sets	: 1
kscratch registers	: 0
core			: 0
VCED exceptions		: not available
VCEI exceptions		: not available

processor		: 1
cpu model		: Cavium Octeon+ V0.1
BogoMIPS		: 1000.00
wait instruction	: yes
microsecond timers	: yes
tlb_entries		: 64
extra interrupt vector	: yes
hardware watchpoint	: yes, count: 2, address/irw mask: [0x0ffc, 0x0ffb]
isa			: mips1 mips2 mips3 mips4 mips5 mips64r2
ASEs implemented	:
shadow register sets	: 1
kscratch registers	: 0
core			: 1
VCED exceptions		: not available
VCEI exceptions		: not available

Repositorio Público de Irontec: packages.irontec.com

Tanto para IvozProvider, SNGREP como de uso interno/público nuestro, en packages.irontec.com se autoconstruyen con Jenkins packages de varios componentes que solemos utilizar a en este tipo de proyectos. Si bien es cierto que en los proyectos principales existen repositorios para Debian oficiales y muy bien mantenidos, para lo que es MIPS, no suelen tener el check marcado de preparar paquetes, dado que es una arquitectura que no se usa mucho. Pero claro está, si queremos utilizar EdgeRouter, tenemos que tener binarios para dicha arquitectura.

Dicho esto, los paquetes que tenemos para MIPS en dicho repo:

  • Kamailio
  • SEMS
  • SNGREP
  • CAPTAGENT
  • Journal2Gelf
  • …y alguno más.

 

Preparando el device

Al ser EdgeOS, tenemos que seguir el guión oficial para añadir repos:

# configure
set system package repository wheezy components 'main contrib non-free'
set system package repository wheezy distribution wheezy 
set system package repository wheezy url http://http.us.debian.org/debian
set system package repository wheezy-security components main
set system package repository wheezy-security distribution wheezy/updates
set system package repository wheezy-security url http://security.debian.org
set system package repository irontec components 'main extra'
set system package repository irontec distribution wheezy 
set system package repository irontec url http://packages.irontec.com/debian
commit
save

Con esto básicamente lo que hacemos es activar los repos de wheezy (los standard, por tema de dependencias), así como el repo de Irontec, donde os hemos dejado preparado SEMS, entre otros.

Sobre el paquete SEMS que os hemos dejado preparado para MIPS, cabe destacar lo siguiente:

  • Hemos quitado toda la parte de RTMP (si, de RTMP, de Adobe Flash).
    • Ha sido por un tema de compilación.
  • La versión de SEMS disponible para MIPS64 – Wheezy es la 1.6
# apt-cache show sems
Package: sems
Version: 1.6.0+0~20171219.4+wheezy~1.gbpef912d
Architecture: mips
Maintainer: Debian VoIP Team <[email protected]>
Installed-Size: 10886
Depends: adduser, python, libc6 (>= 2.4), libcurl3 (>= 7.16.2), libev4 (>= 1:4.04), libevent-2.0-5 (>= 2.0.10-stable), libevent-pthreads-2.0-5 (>= 2.0.10-stable), libgcc1 (>= 1:4.1.1), libhiredis0.10 (>= 0.10.1), libmysql++3, libopus0, libspandsp2 (>= 0.0.6~pre18), libspeex1 (>= 1.2~beta3-1), libssl1.0.0 (>= 1.0.0), libstdc++6 (>= 4.6), libxml2 (>= 2.7.4)

En lo que es una instalación base de un EdgeRouter, sin nada instalado, estas son las dependencias y el espacio que arrastra el apt-get install sems:

The following NEW packages will be installed:
  libev4 libevent-core-2.0-5 libevent-pthreads-2.0-5 libhiredis0.10 libjbig0 libjpeg8 libmysql++3 libmysqlclient18 libopus0
  libspandsp2 libspeex1 libtiff4 mysql-common sems
0 upgraded, 14 newly installed, 0 to remove and 0 not upgraded.
Need to get 6560 kB of archives.
After this operation, 18.4 MB of additional disk space will be used.
Do you want to continue [Y/n]? 

 

Configuración base de SEMS para B2BUA – SBC

En este post, como comentábamos, no tenemos la intención de entrar en toda la potencia de SEMS, queremos simplemente ilustrar la facilidad de despliegue para lo que es una configuración base de tipo B2BUA/SBC, es decir, algo como lo que ilustra este esquema:

Primer paso: Definición de interfaces de escucha y app SBC

SEMS permite ser «multihomed«, con múltiples interfaces de escucha para signalling y media, tantos como queramos y al actuar como B2BUA, no tenemos (o tenemos muchos menos) problemas de routing, de IP’s expuestas vs no expuestas, de interfaces tras NAT vs NO … es decir, nos simplifica mucho la vida.

Para ello, tras la instalación base, la configuración de los interfaces se realiza en /etc/sems/sems.conf:

load_plugins=sbc

interfaces=interno, externo

# Interface Interno 
sip_ip_interno=192.168.2.150
sip_port_interno=5060
media_ip_interno=192.168.2.150
rtp_low_port_interno=50000
rtp_high_port_interno=60000

# Inteface Externo
sip_ip_externo=192.168.1.150
sip_port_externo=5060
media_ip_externo=192.168.1.150
public_ip_externo=8.8.9.9 #FIXME ;)
rtp_low_port_externo=50000
rtp_high_port_externo=60000

application=sbc

De esta configuración, cabe destacar:

  • interfaces: podemos definir tantos como queramos, tal cual.
  • public_ip_[INTERFACE]; Si estamos tras NAT, es la IP que se enviará en los VIA’s o SDP’s

Los demás puntos de configuración son casi «self explanatory«.

Con esto ya tendríamos la parte de interfaces ya lista, no hace falta hacer nada más 🙂

Por último, sobre el tema de interfaces: no estamos obligados a tener varios, es decir, la definición tiene que ser una consecuencia de la necesidad técnica general, no una obligación, es posible que queramos hacer de SBC/B2BUA directamente sobre el mismo interface, no pasa nada, es perfectamente válido usar sólo uno.

Segundo paso: Definición de profiles

Los profiles, por así decirlo son los perfiles de lógicas definibles para la APP SBC. Es decir, en el esquema superior de Alice y Bob es todo muy simple, solo hay dos entidades, pero es posible que en nuestro esquema, tengamos ya más interfaces o en los mismos interfaces diferentes requisitos para lo que son los «call agents».

También es posible que aunque tengamos diferentes interfaces, por cómo es nuestra arquitectura, no tengamos necesidades especiales para cada uno de ellos, y que queramos simplemente enviarlos al mismo profile y listo, en las dos siguientes secciones se entenderá lo que hace cada profile y ahí podremos concluir los que no hacen falta.

Dichos profiles se definen en /etc/sems/etc/sbc.conf:

profiles=interno,externo

En dicho fichero se definen igualmente las reglas de vinculación (en base a método, en base a IP, ….) , las veremos en la siguiente sección.

Continuando: Reglas de asignación a profiles

En lo que es el fichero sbc.conf, se definen igualmente las reglas (cada una luego tendrá su fichero de mapping) para asignar a un perfil concreto cada nueva request.

Sobre esto, destacar que el fichero de ejemplo de la documentación está plenamente detallado y merece la pena tenerlo a mano:

https://github.com/sems-server/sems/blob/master/apps/sbc/etc/sbc.conf

Por norma general, es probable que si estamos simplemente probando, lo que mejor encaje sea el src_ipmap (matchear profile por dirección IP), pero como diseño, si lo estamos basando por un proxy, quizás queramos utilizar una header específica o quizás queramos ser «transparent total» y que se base en la request uri simplemente y fin, asi podría usar tipo «outbound proxy», aportando todo el tema de media relay y topo hiding que suele ser lo buscado.

En nuestro caso, utilizaremos el match por IP, pero insistimos: es únicamente para ilustrar el post y tener una config sencilla funcionando en pocos minutos por cualquiera, no significa que sea el mejor camino ni mucho menos que se adapte a cualquier escenario.

Dicho esto, tendríamos en /etc/sems/etc/sbc.conf:

active_profile=$M($si=>src_ipmap)
regex_maps=src_ipmap

Con esto, lo que estamos diciendo a SEMS es que para determinar el perfil activo en cada request que le llega, se base en el módulo src_ipmap, pasándole la IP origen como parámetro ($si, para muchas cosas tenemos las mismas variables que en OpenSIPS/Kamailio – lo cual facilita todo).

Finalmente, lo que tendríamos en  /etc/sems/etc/src_ipmap.conf:

^192\.168\.1\.150=>interno
^192\.168\.2\.150=>externo

Esta configuración le indica a SEMS que:

  • Si la request viene de 192.168.1.150, el profile a activar es «interno».
  • Si la request viene de 192.168.2.150, el profile a activar es «externo».

Como se ve, es una regex, se pueden utilizar *, se deben escapar los ‘.’, entre otros, lo normal en toda regex.

Llegados a este punto, lo que tenemos, por recapitular es:

  • SEMS escuchando en las IP’s y puertos que queramos.
  • Profiles definidos.
  • Reglas de vinculación a cada profile en base a IP origen definidas.

Nos queda por tanto únicamente definir lo que hay que hacer en cada profile y «fin» 😉

Configurando cada profile

Los profiles se tienen que configurar cada uno en su fichero tal que: [nombre_perfil].sbcprofile.conf, ubicados en el el path /etc/sems/etc (con la versión de la paquetería provista). Por tanto, en nuestro caso lo que tendríamos que crear es:

  • /etc/sems/etc/interno.sbcprofile.conf
  • /etc/sems/etc/externo.sbcprofile.conf

En dicho fichero, una configuración base sería por ejemplo, la más mínima posible:

~# cat /etc/sems/etc/interno.sbcprofile.conf 

dlg_nat_handling=no
transparent_dlg_id=no
next_hop=192.168.1.150:5060
enable_rtprelay=yes
RURI=sip:[email protected]
outbound_interface=externo

Esta configuración para el profile con nombre «interno» lo que hace es, para cualquier request que matchee en este profile:

  • No gestiona el NAT (no nos hace falta en nuestro caso, pero lo podríamos activar)
  • Utiliza 2 callid’s diferentes, es decir, como un B2BUA puro
    • Esto para el tema de REGISTER’s con Asterisk conviene mirarlo con cuidado, porque no se consigue el efecto deseado si se activa.
  • Todas las requests las reenvía a 192.1681.1.150 UDP 5060
    • Este punto es importante: Podemos simplemente reenviarlo a otro destino, como podría ser un proxy y que este último «se busque la vida» o «haga accounting» o lo que queramos, sin tocar nada de la request uri,
  • La request uri la cambia por la misma request uri original que llegaba pero cambio el domain
    • Como decíamos, en este caso porque estamos poniendo en contacto a dos SIP Endpoints directamente, e incluso depende de lo que sean Alice o Bob, por ejemplo, si fueran Asterisk, realmente le da igual el domain, podemos ni tocar la request uri y «se lo tragaría bien».
  • Fuerza que el interface de salida sea «externo»

¿Y que pasa con los REGISTER’s ?

Aquí es dónde SEMS nos hace la vida muy fácil:

# registration cache
enable_reg_caching=yes

Con esto lo que hace es actuar de mid registrar (tal y cómo lo hace OpenSIPS con su mid-registrar module):

  • Se «queda» con la location (Contact).
  • Reenvia un contact con su propia IP (la del SEMS) con un hash.

 

Analizando el rendimiento

Por nuestra tipología de los casos de uso, no nos hemos querido centrar en buscar el máximo de CPS, dado que no no es un factor determinante ni que se vaya a disparar, sino que nos hemos centrado más en el análisis de la capacidad de llamadas concurrentes con media (G711A).

A continuación, tenemos una gráfica ilustrativa (sacada de nuestro querido Observium) de cómo ha estado aguantando la carga, cada 2 minutos hemos lanzado una nueva llamada, es decir, cada hora 30 llamadas paralelas con full media, todas con g711a como codec:

El resultado:

Es decir, podemos decir que este router aguanta unas 100 llamadas full media sin problema alguno, con g729a seguramente se llegue sin problemas con ese mismo device a 250-300.

Si por alguna razón estáis interesados en más capacidad y seguir con la línea de EdgeRouter, el Er8-PRO, de precio también muy razonable, seguro que multiplica esas stats.

Como comentábamos, esto es para determinados casos de uso.

 

Concluyendo, sentando las bases

Con este post, cabe destacar que no estamos haciendo ninguna bomberada, lo que es Ubiquiti, una empresa muy muy grande, trabaja de forma oficial en sus firmwares basados en Debian, y el software utilizado (SEMS), es por el que han apostado grandes players del momento como SIPWISE con su SIPProvider y FRAFOS con su ABC SBC.

Sobre este post, no os quedéis únicamente con la app SBC/B2BUA de SEMS, soporta muchísimas más funciones, con lo que para todos esos casos en los que queremos algo puntual de gestión de media, puede ser un camino firme.

Por resumir las ventajas de este tipo de enfoque, por si algun@ os lo estáis planteando:

  • Aporta el concepto de «entry point» a la red VoIP, es decir, se despliega este dispositivo con una pata hacia la red del cliente, aceptando el direccionamiento que pida.
  • Al ser un dispositivo «en casa del cliente», las capturas pasivas con CAPTAGENT, tanto de signalling como de media (RTCP), van a misa, es decir, nos ahorran muchos problemas de diagnóstico de tramos over wan.
  • Dispone de otras funciones de routing avanzado
    • Si vamos contra una red MPLS, o BGP, o necesitamos túneles (IPSEC, OpenVPN, …), estamos cubiertos.
  • En general, nos aporta visibilidad:
    • CAPTAGENT para enviar a un HOMER y tener visibilidad SIP/RTCP plena.
    • NETFLOW para enviar a un NETFLOW Analyzer y tener visibilidad de flujos.

Como limitación importante de SEMS en su versión open source, por si os lo estáis planteando desplegar de forma masiva, cabe destacar la ausencia de protocolo TLS de transporte.

 



¿Te gusta este post? Es solo un ejemplo de cómo podemos ayudar a tu empresa...
Sobre Gorka Gorrotxategi

CTO en Irontec, en el frente técnico desde un par de lustros ya, para todo lo que tenga que ver con Networking, VoIP y Sistemas, en ese orden :D) Desde @zetagor escribo algo, pero poco verbose la verdad

1 Comentario

¿Por qué no comentas tú también?

Queremos tu opinión :)