Skip to content

Security

github-actions[bot] edited this page Mar 23, 2026 · 20 revisions

Security

The matlab-mcp-server includes multiple security layers to prevent misuse while keeping MATLAB accessible to AI agents. This page details authentication, authorization, input validation, secure configuration, and deployment best practices.

Authentication & Authorization

Transport-Level Authentication

The server supports two transport modes with different auth models:

Stdio Transport (Single User)

  • Default mode — suitable for local development and single-user deployments
  • Authentication: Handled by the process that spawns the server (e.g., Claude Desktop, local agent)
  • No explicit auth in server — the OS process boundary provides isolation

SSE Transport (Multi-User)

  • Stateful HTTP connection — suitable for shared server deployments
  • Authentication: Must be provided by a reverse proxy (nginx, Caddy, Traefik, etc.)
  • Server-side flag: Set security.require_proxy_auth: true to acknowledge your auth setup
  • Critical: Do NOT expose the SSE port directly to the internet

Session Management

Each connection (stdio or SSE) gets a session ID that isolates:

  • MATLAB workspace variables
  • Temporary files and job results
  • Job tracking and history

Sessions are automatically cleaned up after session_timeout seconds of inactivity (default 1 hour) and can be explicitly destroyed via API.

sessions:
  max_sessions: 50              # Limit concurrent sessions
  session_timeout: 3600         # Expire after 1 hour idle
  job_retention_seconds: 86400  # Keep job metadata for 24 hours

Input Validation & Sanitization

Function Blocklist

By default, these dangerous MATLAB functions are blocked:

Function Risk Blocked By
system() Execute arbitrary OS commands Pattern matching
unix() Execute Unix commands Pattern matching
dos() Execute DOS/Windows commands Pattern matching
! Shell escape operator (e.g., !ls) Line-start pattern
eval() Execute arbitrary string as code Pattern matching
feval() Call function by name string Pattern matching
evalc() Evaluate and capture output Pattern matching
evalin() Evaluate in caller/base workspace Pattern matching
assignin() Assign variable in caller/base workspace Pattern matching
perl() Execute Perl scripts Pattern matching
python() Execute Python scripts Pattern matching

Smart Code Scanning

The SecurityValidator uses intelligent pattern matching that strips string literals and comments before checking for blocked functions. This prevents false positives:

% These are SAFE and will NOT trigger the blocklist:
disp('The system is great')              % "system" inside a string
msg = "unix-based systems";              % "unix" inside a string
% This code uses system('ls')            % Entire comment is ignored

% These WILL be blocked:
system('rm -rf /')                       % Actual system() call
[status, output] = unix('ls /tmp');      % Actual unix() call
!ls -la                                  % Shell escape at line start

Implementation details:

  • Regex-based patterns with word boundaries (\bsystem\b)
  • String literal removal handles both 'single' and "double" quotes
  • Comment stripping removes % to end of line
  • False-positive rate is extremely low for legitimate MATLAB code

Filename Sanitization

File operations (upload, download, delete) are protected against path traversal attacks:

# Allowed filenames:  data.csv, my_script.m, results_2024.xlsx
# Blocked filenames:  ../etc/passwd, /etc/shadow, ../../secrets.txt
# Reason: Contain path separators or '..' traversal patterns

The validator:

  1. Rejects filenames with / or \
  2. Rejects filenames starting with /
  3. Rejects sequences like .. or ./
  4. Allows only alphanumeric, dots, underscores, and hyphens: [a-zA-Z0-9._-]+
  5. All file I/O is confined to the session's temp directory

Upload Size Limits

security:
  max_upload_size_mb: 100       # Default: 100 MB per file

Files exceeding this limit are rejected before writing to disk. This prevents:

  • Disk exhaustion attacks
  • Memory exhaustion during decoding
  • Extremely long processing times

Security-Related Configuration

Core Security Settings

security:
  # Block dangerous MATLAB functions (recommended: enabled)
  blocked_functions_enabled: true
  
  # Customizable list of blocked functions
  blocked_functions:
    - "system"
    - "unix"
    - "dos"
    - "!"
    - "eval"
    - "feval"
    - "evalc"
    - "evalin"
    - "assignin"
    - "perl"
    - "python"
    # Add custom entries as needed for your org
  
  # File upload size limit
  max_upload_size_mb: 100
  
  # Multi-user deployment flag (SSE only)
  require_proxy_auth: false  # Set to true when behind reverse proxy

Workspace Isolation

execution:
  # Automatically clear workspace between sessions
  workspace_isolation: true

When enabled (default), the server runs these commands when a session starts:

clear all;
clear global;
clear functions;
fclose all;
restoredefaultpath;

This ensures:

  • Variables from previous sessions are erased
  • Function definitions don't persist across users
  • File handles are closed (preventing lock issues)
  • MATLAB path is reset to defaults

Recommended Config Values

Personal/Local Development

server:
  transport: "stdio"    # Safest default

security:
  blocked_functions_enabled: true
  max_upload_size_mb: 100

execution:
  workspace_isolation: true

sessions:
  max_sessions: 5
  session_timeout: 3600

Team Server (Behind Reverse Proxy)

server:
  transport: "sse"
  host: "127.0.0.1"     # Bind to localhost only

security:
  blocked_functions_enabled: true
  require_proxy_auth: true  # You handle auth in proxy
  max_upload_size_mb: 500

execution:
  workspace_isolation: true

sessions:
  max_sessions: 50
  session_timeout: 1800    # Shorter timeout for shared server

monitoring:
  enabled: true           # Track who does what

Production Deployment

server:
  transport: "sse"
  host: "127.0.0.1"
  port: 8765              # Use internal port only

security:
  blocked_functions_enabled: true
  require_proxy_auth: true
  max_upload_size_mb: 250

execution:
  workspace_isolation: true
  max_execution_time: 300  # Shorter timeout

sessions:
  max_sessions: 100
  session_timeout: 900     # 15 minutes
  job_retention_seconds: 3600  # Keep results 1 hour only

monitoring:
  enabled: true
  retention_days: 30       # Audit trail

Secure Deployment & Operation

Architecture Overview

graph TB
    subgraph Agent["AI Agent (Claude, etc)"]
        A["MCP Client"]
    end
    
    subgraph Transport["Transport Layer"]
        B["Stdio OR SSE"]
    end
    
    subgraph Auth["Authentication"]
        C["Process Boundary<br/>(Stdio) OR<br/>Reverse Proxy<br/>(SSE)"]
    end
    
    subgraph Server["MATLAB MCP Server"]
        D["Session Manager<br/>(Isolation)"]
        E["Security Validator<br/>(Function Blocklist)"]
        F["Job Executor"]
    end
    
    subgraph Engine["MATLAB Engine"]
        G["Workspace<br/>(Cleared per session)"]
    end
    
    A -->|Stdio| B
    A -->|SSE| B
    B --> C
    C --> D
    D --> E
    E --> F
    F --> G
    
    style A fill:#e1f5ff
    style C fill:#fff3e0
    style D fill:#f3e5f5
    style E fill:#fce4ec
    style F fill:#e8f5e9
    style G fill:#f1f8e9
Loading

Stdio Transport (Development/Local)

Best for: Single user, local development, testing

# Run server in local development
matlab-mcp --config ./config.yaml

# Connected to by Claude Desktop or local agent via stdio

Security properties:

  • OS process isolation (spawned process inherits parent's security context)
  • No network exposure
  • Session = process instance
  • Cleanup = process termination

SSE Transport (Multi-User Server)

Best for: Shared deployments, team environments, CI/CD systems

graph LR
    subgraph Clients["External Clients"]
        C1["Agent 1"]
        C2["Agent 2"]
        C3["Agent N"]
    end
    
    subgraph Proxy["Reverse Proxy Layer<br/>(Authentication + TLS)"]
        P["nginx / Caddy / Traefik<br/>+ OAuth / SAML / Basic Auth"]
    end
    
    subgraph Server["MATLAB MCP Server<br/>(Internal Network)"]
        S["SSE Port 8765<br/>Localhost Only"]
    end
    
    subgraph MATLAB["MATLAB Engines"]
        E1["Engine 1<br/>(Session 1)"]
        E2["Engine 2<br/>(Session 2)"]
        E3["Engine N<br/>(Session N)"]
    end
    
    C1 -->|HTTPS| P
    C2 -->|HTTPS| P
    C3 -->|HTTPS| P
    P -->|HTTP<br/>127.0.0.1:8765| S
    S --> E1
    S --> E2
    S --> E3
    
    style P fill:#fff3e0
    style S fill:#e3f2fd
    style MATLAB fill:#e8f5e9
Loading

Setup checklist:

  • Reverse proxy configured with authentication (OAuth, SAML, etc.)
  • MATLAB MCP server bound to 127.0.0.1:8765 (internal only)
  • TLS/HTTPS enforced on proxy
  • require_proxy_auth: true set in config
  • Firewall rules restrict port 8765 to proxy only
  • Monitoring enabled for audit trail

Example nginx config:

server {
    listen 443 ssl;
    server_name matlab-server.example.com;
    
    ssl_certificate /etc/ssl/certs/cert.pem;
    ssl_certificate_key /etc/ssl/private/key.pem;
    
    # Add your auth module here (oauth2_proxy, etc.)
    auth_request /oauth2/auth;
    
    location / {
        proxy_pass http://127.0.0.1:8765;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        
        # SSE requires special headers
        proxy_buffering off;
        proxy_cache off;
    }
}

Docker Deployment

# docker-compose.yml example with security hardening
version: "3"
services:
  matlab-mcp:
    image: matlab-mcp-server:latest
    container_name: matlab-mcp
    
    # Security: non-root user
    user: "1000:1000"
    
    # Read-only root filesystem
    read_only: true
    
    # Limited capabilities
    cap_drop:
      - ALL
    cap_add:
      - NET_BIND_SERVICE
    
    # Internal network only
    networks:
      - internal
    
    # Volume mounts
    volumes:
      - ./config.yaml:/app/config.yaml:ro
      - ./custom_tools.yaml:/app/custom_tools.yaml:ro
      - matlab_temp:/app/temp
      - matlab_results:/app/results
      - matlab_monitoring:/app/monitoring
    
    # Env-based overrides (no hardcoded secrets!)
    environment:
      - MATLAB_MCP_LOG_LEVEL=info
      - MATLAB_MCP_SECURITY_BLOCKED_FUNCTIONS_ENABLED=true
    
    # Resource limits
    deploy:
      resources:
        limits:
          cpus: "4"
          memory: 8G
        reservations:
          cpus: "2"
          memory: 4G

  # Reverse proxy (not exposed to internet)
  reverse-proxy:
    image: nginx:latest
    networks:
      - internal
    ports:
      - "8443:443"  # External HTTPS only
    volumes:
      - ./nginx.conf:/etc/nginx/nginx.conf:ro
      - ./certs:/etc/nginx/certs:ro

networks:
  internal:
    driver: bridge
    driver_opts:
      com.docker.network.bridge.name: br-internal

volumes:
  matlab_temp:
  matlab_results:
  matlab_monitoring:

Logging & Monitoring

monitoring:
  enabled: true
  sample_interval: 10          # Collect metrics every 10 seconds
  retention_days: 30           # Keep 30 days of history
  db_path: ./monitoring/metrics.db
  dashboard_enabled: true

Events captured:

  • Job completion / failure
  • Session creation / destruction
  • Blocked function attempts (security violations)
  • Engine scale-up / scale-down events
  • Health check failures
  • Execution duration and memory usage

Use the dashboard (http://localhost:8766/dashboard) to monitor:

  • Pool utilization and engine count
  • Job throughput and error rates
  • Execution time percentiles (avg, p95)
  • System metrics (memory, CPU)
  • Event log with severity filtering

Regular Security Reviews

  1. Check blocked function list — Are there new dangerous functions to add?
  2. Review logs — Look for patterns of blocked attempts or unusual behavior
  3. Update MATLAB — Keep MATLAB Engine API updated with security patches
  4. Audit custom tools — Do custom MATLAB functions need additional restrictions?
  5. Rotate proxy credentials — If using API keys or OAuth secrets

Reporting Security Vulnerabilities

Security Issues

If you discover a security vulnerability in the MATLAB MCP server:

  1. Do NOT open a public GitHub issue — This could enable exploitation
  2. Email the maintainer — Use the contact information in the repository
  3. Include details:
    • Description of the vulnerability
    • Steps to reproduce
    • Potential impact
    • Suggested fix (if you have one)

Expected Response

  • Acknowledgment within 48 hours
  • Triage and severity assessment within 1 week
  • Timeline for patch release (critical: within 2 weeks)
  • Credit in release notes (optional)

Known Limitations

The following are NOT considered security vulnerabilities:

  • Users can disable the blocklist entirely (blocked_functions_enabled: false) — this is intentional for advanced use cases
  • SSE transport without a reverse proxy — this is a misconfiguration, not a bug
  • MATLAB code that exhausts memory or CPU — this is a resource limit issue (set max_execution_time)
  • Custom MATLAB functions that execute dangerous operations — users are responsible for vetting custom tools

Best Practices Summary

graph TD
    A["Security Best Practices"]
    
    B["Authentication"]
    C["Input Validation"]
    D["Configuration"]
    E["Operations"]
    
    A --> B
    A --> C
    A --> D
    A --> E
    
    B --> B1["Use reverse proxy<br/>for multi-user"]
    B --> B2["Enable TLS/HTTPS<br/>in production"]
    B --> B3["Bind to localhost<br/>on SSE"]
    
    C --> C1["Keep blocklist enabled<br/>by default"]
    C --> C2["Customize blocklist<br/>for your org"]
    C --> C3["Monitor blocked<br/>attempts in logs"]
    
    D --> D1["Set workspace_isolation=true"]
    D --> D2["Limit upload size<br/>appropriately"]
    D --> D3["Set short timeouts<br/>in production"]
    
    E --> E1["Enable monitoring<br/>and logging"]
    E --> E2["Review logs regularly"]
    E --> E3["Update MATLAB<br/>and dependencies"]
    E --> E4["Test before deploying<br/>to production"]
    
    style B fill:#e3f2fd
    style C fill:#f3e5f5
    style D fill:#fff3e0
    style E fill:#e8f5e9
Loading
Scenario Key Actions
Local Development Use stdio transport, default config
Team Server SSE + reverse proxy + auth, enable monitoring
Production All of team + TLS, short timeouts, audit logs, incident response plan

Clone this wiki locally