Identificación de Sistema Operativo por TTL (Time To Live)
Identificación de Sistema Operativo por TTL
Section titled “Identificación de Sistema Operativo por TTL”Introducción
Section titled “Introducción”El Time To Live (TTL) es un campo fundamental en los protocolos de red que juega un papel crucial en la identificación de sistemas operativos durante el reconocimiento y escaneo en pentesting.
¿Qué es el TTL?
Section titled “¿Qué es el TTL?”El tiempo de vida (TTL) hace referencia a la cantidad de tiempo o “saltos” que se ha establecido que un paquete debe existir dentro de una red antes de ser descartado por un enrutador. El TTL también se utiliza en otros contextos, como el almacenamiento en caché de CDN y el almacenamiento en caché de DNS.
Funcionamiento del TTL
Section titled “Funcionamiento del TTL”Cuando se crea un paquete de información y se envía a través de Internet, existe el riesgo de que siga pasando de enrutador a enrutador indefinidamente. Para mitigar esta posibilidad, los paquetes se diseñan con una caducidad denominada tiempo de vida o límite de saltos.
Proceso del TTL:
- Cada paquete tiene un valor numérico que determina cuánto tiempo debe seguir moviéndose por la red
- Cada vez que un enrutador recibe un paquete, resta uno al recuento de TTL
- Si el recuento de TTL llega a cero después de la resta, el enrutador:
- Descarta el paquete
- Envía un mensaje ICMP (Time Exceeded) al host de origen
Aplicaciones del TTL
Section titled “Aplicaciones del TTL”- Prevención de bucles infinitos en redes
- Información de trayectoria de paquetes
- Diagnóstico de redes (traceroute)
- Fingerprinting de sistemas operativos
- Detección de manipulación de paquetes
Relación con la Identificación de Sistema Operativo
Section titled “Relación con la Identificación de Sistema Operativo”Diferentes sistemas operativos tienen diferentes valores predeterminados de TTL. Esta diferencia se debe a las implementaciones específicas de la pila TCP/IP en cada sistema operativo.
Lógica de Identificación
Section titled “Lógica de Identificación”Si enviamos un paquete a una máquina y recibimos una respuesta:- TTL = 128 → Probablemente Windows- TTL = 64 → Probablemente Linux/Unix- TTL = 255 → Probablemente Cisco/Redes- Otros valores → Requiere análisis adicional¿Por qué varían los valores TTL por defecto?
Section titled “¿Por qué varían los valores TTL por defecto?”Los valores TTL predeterminados se establecen en el kernel de cada sistema operativo:
- Windows: TTL = 128 (desde Windows NT)
- Linux: TTL = 64 (valor estándar)
- macOS: TTL = 64
- Solaris: TTL = 255
- Cisco IOS: TTL = 255
- HP-UX: TTL = 64
Tabla Completa de Valores TTL
Section titled “Tabla Completa de Valores TTL”Basado en la investigación de Subin’s Blog (https://subinsb.com/default-device-ttl-values/), aquí está la tabla completa de valores TTL por defecto:
Sistemas Operativos de Escritorio
Section titled “Sistemas Operativos de Escritorio”| Sistema Operativo | Versión | TTL Predeterminado | Protocolo |
|---|---|---|---|
| Windows | NT 4.0 | 128 | TCP |
| Windows | 2000 | 128 | TCP |
| Windows | XP | 128 | TCP |
| Windows | Vista | 128 | TCP |
| Windows | 7 | 128 | TCP |
| Windows | 8 | 128 | TCP |
| Windows | 10 | 128 | TCP |
| Windows | Server 2003 | 128 | TCP |
| Windows | Server 2008 | 128 | TCP |
| Windows | Server 2012 | 128 | TCP |
| Linux | Kernel 2.4 | 64 | TCP |
| Linux | Kernel 2.6 | 64 | TCP |
| Linux | Kernel 3.x | 64 | TCP |
| Linux | Kernel 4.x | 64 | TCP |
| Linux | Kernel 5.x | 64 | TCP |
| macOS | 10.x | 64 | TCP |
| FreeBSD | Todas | 64 | TCP |
| OpenBSD | Todas | 64 | TCP |
| NetBSD | Todas | 64 | TCP |
Dispositivos de Red y Servidores
Section titled “Dispositivos de Red y Servidores”| Dispositivo/SO | Versión | TTL Predeterminado | Protocolo |
|---|---|---|---|
| Cisco IOS | 12.x | 255 | TCP |
| Cisco IOS | 15.x | 255 | TCP |
| Juniper | JUNOS | 64 | TCP |
| HP-UX | 11.x | 64 | TCP |
| Solaris | 8 | 64 | TCP |
| Solaris | 9 | 64 | TCP |
| Solaris | 10 | 64 | TCP |
| AIX | 5.x | 64 | TCP |
| AIX | 6.x | 64 | TCP |
Dispositivos Móviles
Section titled “Dispositivos Móviles”| Dispositivo | Sistema | TTL Predeterminado | Protocolo |
|---|---|---|---|
| iPhone | iOS | 64 | TCP |
| Android | 4.x | 64 | TCP |
| Android | 5.x | 64 | TCP |
| Android | 6.x | 64 | TCP |
| Android | 7.x | 64 | TCP |
| Android | 8.x | 64 | TCP |
| Android | 9.x | 64 | TCP |
| Android | 10.x | 64 | TCP |
Valores TTL en ICMP vs TCP
Section titled “Valores TTL en ICMP vs TCP”| Sistema Operativo | TTL ICMP | TTL TCP | Observaciones |
|---|---|---|---|
| Windows | 128 | 128 | Consistente |
| Linux | 64 | 64 | Consistente |
| macOS | 64 | 64 | Consistente |
| Cisco | 255 | 255 | Consistente |
| Algunos routers | Variable | Variable | Depende de configuración |
Script Python: WhichSystem
Section titled “Script Python: WhichSystem”Versión Mejorada
Section titled “Versión Mejorada”#!/usr/bin/env python3# -*- coding: utf-8 -*-"""WhichSystem - Identificación de Sistema Operativo por TTLVersión mejorada con más funcionalidades
Uso: python3 whichsystem.py <direccion-ip>"""
import reimport sysimport subprocessimport argparseimport socketfrom typing import Optional, Tuple
class OSFingerprint: """Clase para fingerprinting de SO basado en TTL"""
# Base de datos de valores TTL por SO OS_DATABASE = { 'Windows': { 'range': (65, 128), 'default_ttl': 128, 'description': 'Sistema operativo Windows (NT/2000/XP/Vista/7/8/10/Server)' }, 'Linux': { 'range': (1, 64), 'default_ttl': 64, 'description': 'Sistema operativo Linux/Unix (Kernel 2.x-5.x)' }, 'macOS': { 'range': (1, 64), 'default_ttl': 64, 'description': 'macOS/iOS (Darwin kernel)' }, 'Cisco': { 'range': (129, 255), 'default_ttl': 255, 'description': 'Dispositivo Cisco (IOS/NX-OS)' }, 'Solaris': { 'range': (1, 64), 'default_ttl': 64, 'description': 'Oracle Solaris' }, 'FreeBSD': { 'range': (1, 64), 'default_ttl': 64, 'description': 'FreeBSD/OpenBSD/NetBSD' } }
@staticmethod def get_ttl_ping(ip_address: str, count: int = 1) -> Optional[int]: """ Obtiene el TTL usando ping
Args: ip_address: Dirección IP objetivo count: Número de paquetes ping
Returns: TTL del paquete recibido o None si falla """ try: # Comando ping según el sistema operativo if sys.platform.startswith('win'): cmd = ['ping', '-n', str(count), ip_address] else: cmd = ['ping', '-c', str(count), ip_address]
proc = subprocess.Popen( cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True )
stdout, stderr = proc.communicate(timeout=10)
if proc.returncode != 0: print(f"[!] Error al hacer ping: {stderr}") return None
# Extraer TTL de la respuesta # Buscar patrón TTL en diferentes idiomas ttl_patterns = [ r'TTL=(\d+)', r'ttl=(\d+)', r'Tiempo de vida (\d+)', r'ttl\s+(\d+)' ]
for pattern in ttl_patterns: match = re.search(pattern, stdout, re.IGNORECASE) if match: return int(match.group(1))
print("[!] No se pudo extraer TTL de la respuesta") return None
except subprocess.TimeoutExpired: print("[!] Timeout en ping") return None except Exception as e: print(f"[!] Error ejecutando ping: {e}") return None
@staticmethod def get_ttl_traceroute(ip_address: str) -> Optional[int]: """ Obtiene el TTL usando traceroute (método alternativo)
Args: ip_address: Dirección IP objetivo
Returns: TTL estimado o None si falla """ try: if sys.platform.startswith('win'): cmd = ['tracert', '-d', '-h', '1', ip_address] else: cmd = ['traceroute', '-n', '-m', '1', ip_address]
proc = subprocess.Popen( cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE, universal_newlines=True )
stdout, stderr = proc.communicate(timeout=15)
# traceroute muestra el TTL que causó el timeout # Buscar el último salto antes del destino lines = stdout.split('\n') for line in reversed(lines): if '*' not in line and line.strip(): # Extraer el número del primer campo (salto) parts = line.split() if len(parts) >= 2: try: hop_number = int(parts[0]) return hop_number + 1 # TTL aproximado except ValueError: continue
return None
except Exception as e: print(f"[!] Error en traceroute: {e}") return None
@classmethod def identify_os(cls, ttl: int) -> dict: """ Identifica el SO basado en el valor TTL
Args: ttl: Valor TTL obtenido
Returns: Diccionario con información del SO identificado """ for os_name, os_info in cls.OS_DATABASE.items(): min_ttl, max_ttl = os_info['range'] if min_ttl <= ttl <= max_ttl: return { 'os': os_name, 'confidence': cls._calculate_confidence(ttl, os_info['default_ttl']), 'description': os_info['description'], 'ttl_range': os_info['range'], 'default_ttl': os_info['default_ttl'] }
return { 'os': 'Desconocido', 'confidence': 0, 'description': f'TTL {ttl} no coincide con valores conocidos', 'ttl_range': None, 'default_ttl': None }
@staticmethod def _calculate_confidence(actual_ttl: int, default_ttl: int) -> float: """ Calcula la confianza de la identificación
Args: actual_ttl: TTL recibido default_ttl: TTL por defecto del SO
Returns: Porcentaje de confianza (0-100) """ if actual_ttl == default_ttl: return 100.0 elif abs(actual_ttl - default_ttl) <= 5: return 80.0 elif abs(actual_ttl - default_ttl) <= 10: return 60.0 else: return 40.0
@staticmethod def validate_ip(ip_address: str) -> bool: """ Valida que la dirección IP sea correcta
Args: ip_address: Dirección IP a validar
Returns: True si es válida, False en caso contrario """ try: socket.inet_aton(ip_address) return True except socket.error: return False
def main(): parser = argparse.ArgumentParser( description='WhichSystem - Identificación de SO por TTL', formatter_class=argparse.RawDescriptionHelpFormatter, epilog="""Ejemplos de uso: python3 whichsystem.py 192.168.1.1 python3 whichsystem.py -v 10.10.10.188 python3 whichsystem.py --traceroute 8.8.8.8 """ )
parser.add_argument('ip', help='Dirección IP objetivo') parser.add_argument('-v', '--verbose', action='store_true', help='Modo verbose con más información') parser.add_argument('-t', '--traceroute', action='store_true', help='Usar traceroute en lugar de ping') parser.add_argument('-c', '--count', type=int, default=1, help='Número de paquetes ping (default: 1)')
args = parser.parse_args()
# Validar IP if not OSFingerprint.validate_ip(args.ip): print(f"[!] Dirección IP inválida: {args.ip}") sys.exit(1)
print(f"[+] Analizando {args.ip}...") print("-" * 50)
# Obtener TTL if args.traceroute: ttl = OSFingerprint.get_ttl_traceroute(args.ip) method = "traceroute" else: ttl = OSFingerprint.get_ttl_ping(args.ip, args.count) method = "ping"
if ttl is None: print("[!] No se pudo obtener TTL") sys.exit(1)
print(f"[+] Método usado: {method}") print(f"[+] TTL recibido: {ttl}") print("-" * 30)
# Identificar SO result = OSFingerprint.identify_os(ttl)
print(f"[+] Sistema Operativo: {result['os']}") print(f"[+] Confianza: {result['confidence']}%") print(f"[+] Descripción: {result['description']}")
if args.verbose and result['ttl_range']: print(f"[+] Rango TTL esperado: {result['ttl_range'][0]}-{result['ttl_range'][1]}") print(f"[+] TTL por defecto: {result['default_ttl']}")
print("-" * 50)
# Advertencias if result['confidence'] < 70: print("[!] ADVERTENCIA: Baja confianza en la identificación") print(" Posibles causas:") print(" - Firewall modificando TTL") print(" - Router intermedio") print(" - Configuración personalizada del SO") print(" - Red compleja (NAT, VPN, etc.)")
if __name__ == '__main__': try: main() except KeyboardInterrupt: print("\n[!] Interrumpido por el usuario") sys.exit(1) except Exception as e: print(f"[!] Error inesperado: {e}") sys.exit(1)Versión Original (Simplificada)
Section titled “Versión Original (Simplificada)”#!/usr/bin/python3#coding: utf-8
import re, sys, subprocess
# python3 wichSystem.py 10.10.10.188
if len(sys.argv) != 2: print("\n[!] Uso: python3 " + sys.argv[0] + " <direccion-ip>\n") sys.exit(1)
def get_ttl(ip_address):
proc = subprocess.Popen(["/usr/bin/ping -c 1 %s" % ip_address, ""], stdout=subprocess.PIPE, shell=True) (out,err) = proc.communicate()
out = out.split() out = out[12].decode('utf-8')
ttl_value = re.findall(r"\d{1,3}", out)[0]
return ttl_value
def get_os(ttl):
ttl = int(ttl)
if ttl >= 0 and ttl <= 64: return "Linux" elif ttl >= 65 and ttl <= 128: return "Windows" else: return "Not Found"
if __name__ == '__main__':
ip_address = sys.argv[1]
ttl = get_ttl(ip_address)
os_name = get_os(ttl) print("\n%s (ttl -> %s): %s\n" % (ip_address, ttl, os_name))Casos Prácticos
Section titled “Casos Prácticos”Ejemplo 1: Identificación Básica
Section titled “Ejemplo 1: Identificación Básica”# Identificación de Windows$ python3 whichsystem.py 192.168.1.100[+] Analizando 192.168.1.100...--------------------------------------------------[+] Método usado: ping[+] TTL recibido: 128------------------------------[+] Sistema Operativo: Windows[+] Confianza: 100%[+] Descripción: Sistema operativo Windows (NT/2000/XP/Vista/7/8/10/Server)--------------------------------------------------Ejemplo 2: Identificación de Linux
Section titled “Ejemplo 2: Identificación de Linux”# Identificación de Linux$ python3 whichsystem.py 10.10.10.188[+] Analizando 10.10.10.188...--------------------------------------------------[+] Método usado: ping[+] TTL recibido: 63------------------------------[+] Sistema Operativo: Linux[+] Confianza: 80%[+] Descripción: Sistema operativo Linux/Unix (Kernel 2.x-5.x)--------------------------------------------------Ejemplo 3: Caso con Baja Confianza
Section titled “Ejemplo 3: Caso con Baja Confianza”# Caso con modificaciones de red$ python3 whichsystem.py 172.16.1.50[+] Analizando 172.16.1.50...--------------------------------------------------[+] Método usado: ping[+] TTL recibido: 45------------------------------[+] Sistema Operativo: Linux[+] Confianza: 40%[+] Descripción: Sistema operativo Linux/Unix (Kernel 2.x-5.x)--------------------------------------------------[!] ADVERTENCIA: Baja confianza en la identificación Posibles causas: - Firewall modificando TTL - Router intermedio - Configuración personalizada del SO - Red compleja (NAT, VPN, etc.)Limitaciones del Método
Section titled “Limitaciones del Método”Factores que afectan la precisión
Section titled “Factores que afectan la precisión”-
Firewalls y Dispositivos de Red:
- Algunos firewalls modifican el TTL
- Load balancers pueden cambiar valores
- NAT puede afectar los valores
-
Configuraciones Personalizadas:
- Administradores pueden cambiar TTL por defecto
- Scripts de hardening modifican valores
- Contenedores (Docker) pueden tener TTL diferente
-
Redes Complejas:
- VPNs pueden modificar TTL
- Redes corporativas con múltiples saltos
- Cloud providers (AWS, Azure, GCP)
-
Dispositivos Intermedios:
- Routers y switches pueden decrementar TTL
- Proxies transparentes
- Sistemas de IDS/IPS
Precisión por Sistema Operativo
Section titled “Precisión por Sistema Operativo”| Sistema Operativo | Precisión Estimada | Factores de Interferencia |
|---|---|---|
| Windows | 90-95% | Firewall de Windows |
| Linux | 85-90% | Distribuciones modificadas |
| macOS | 80-85% | Configuraciones personalizadas |
| Cisco | 95%+ | Rara modificación |
| Dispositivos IoT | 70-80% | Firmwares personalizados |
Técnicas Complementarias
Section titled “Técnicas Complementarias”Combinar con otros métodos de fingerprinting
Section titled “Combinar con otros métodos de fingerprinting”def comprehensive_fingerprint(ip_address): """ Fingerprinting combinado: TTL + otros métodos """ results = {}
# TTL Analysis ttl = OSFingerprint.get_ttl_ping(ip_address) results['ttl_analysis'] = OSFingerprint.identify_os(ttl) if ttl else None
# Port scanning (simulado) results['open_ports'] = check_common_ports(ip_address)
# Service banners results['service_banners'] = get_service_banners(ip_address)
# HTTP headers results['http_headers'] = get_http_headers(ip_address)
# Combinar resultados return combine_fingerprint_results(results)
def combine_fingerprint_results(results): """ Combina múltiples técnicas para mayor precisión """ confidence_scores = { 'Windows': 0, 'Linux': 0, 'macOS': 0, 'Cisco': 0 }
# TTL aporta 40% de confianza if results['ttl_analysis']: os_from_ttl = results['ttl_analysis']['os'] confidence_scores[os_from_ttl] += 40
# Puertos comunes aportan 30% if 445 in results['open_ports']: # SMB confidence_scores['Windows'] += 30 if 22 in results['open_ports']: # SSH confidence_scores['Linux'] += 20
# HTTP headers aportan 20% if 'IIS' in str(results['http_headers']): confidence_scores['Windows'] += 20 if 'Apache' in str(results['http_headers']): confidence_scores['Linux'] += 15
# Determinar SO más probable best_os = max(confidence_scores, key=confidence_scores.get) best_score = confidence_scores[best_os]
return { 'os': best_os, 'confidence': best_score, 'method': 'combined_fingerprint' }Uso en Nmap
Section titled “Uso en Nmap”# Nmap tiene opciones específicas para TTLnmap -O --osscan-guess 192.168.1.100
# Fingerprinting agresivonmap -O -v --version-intensity 9 192.168.1.100
# Combinar con TTL manualnmap -sP --packet-trace 192.168.1.100Mejores Prácticas
Section titled “Mejores Prácticas”Para Pentesters
Section titled “Para Pentesters”-
Usar múltiples técnicas:
- Combinar TTL con fingerprinting de servicios
- Verificar con herramientas como Nmap
- Analizar banners de servicios
-
Considerar el contexto de red:
- Redes corporativas pueden tener reglas específicas
- Cloud providers modifican TTL
- VPNs afectan los valores
-
Documentar hallazgos:
- Registrar método usado
- Nivel de confianza obtenido
- Factores que pueden afectar precisión
Para Administradores de Sistema
Section titled “Para Administradores de Sistema”-
Configurar TTL apropiado:
Terminal window # Linux - Cambiar TTL por defectosysctl -w net.ipv4.ip_default_ttl=128# Windows - Registryreg add HKLM\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters /v DefaultTTL /t REG_DWORD /d 128 -
Monitorear cambios:
- Usar herramientas de monitoreo de red
- Logs de firewall
- Alertas de cambios inusuales
Consideraciones de Seguridad
Section titled “Consideraciones de Seguridad”Riesgos del Método
Section titled “Riesgos del Método”-
No es 100% confiable:
- Puede dar falsos positivos
- Configuraciones modifican resultados
- No debe usarse como única fuente
-
Consideraciones éticas:
- Usar solo en sistemas autorizados
- Parte de reconocimiento pasivo
- No genera alertas en sistemas objetivo
Recomendaciones de Uso
Section titled “Recomendaciones de Uso”- Usar como complemento: Combinar con otras técnicas
- Verificar resultados: No confiar únicamente en TTL
- Documentar metodología: Para auditorías y reportes
- Mantener actualizado: Los valores pueden cambiar
Recursos Adicionales
Section titled “Recursos Adicionales”Herramientas Relacionadas
Section titled “Herramientas Relacionadas”- Nmap:
nmap -Opara OS fingerprinting completo - P0f: Passive OS fingerprinting
- SinFP: Advanced OS fingerprinting
- Xprobe2: Remote OS detection
Referencias
Section titled “Referencias”- RFC 791: Internet Protocol (TTL original)
- RFC 1812: Requirements for IP Version 4 Routers
- Subin’s Blog: https://subinsb.com/default-device-ttl-values/
- WhichSystem Script: https://pastebin.com/HmBcu7j2
Lecturas Recomendadas
Section titled “Lecturas Recomendadas”- “The Art of Deception” - Kevin Mitnick
- “Hacking: The Art of Exploitation” - Jon Erickson
- “Network Security Assessment” - Chris McNab
Conclusiones
Section titled “Conclusiones”La identificación de sistemas operativos por TTL es una técnica simple pero efectiva que forma parte del arsenal básico de cualquier profesional de seguridad. Aunque no es infalible, proporciona información valiosa cuando se combina con otras técnicas de fingerprinting.
Puntos Clave:
Section titled “Puntos Clave:”- TTL varía por SO: Windows=128, Linux=64, Cisco=255
- Método pasivo: No genera logs en el objetivo
- Limitaciones conocidas: Firewalls y configuraciones afectan precisión
- Complementario: Mejor usado con otras técnicas (Nmap, banners, etc.)
- Útil en reconocimiento: Primera aproximación rápida al SO
Recomendación Final:
Section titled “Recomendación Final:”Usa el TTL como primera aproximación en el reconocimiento, pero siempre verifica con múltiples técnicas antes de llegar a conclusiones definitivas sobre el sistema operativo objetivo.
Última actualización: 2025-01-23 Versión: 2.0