The Model Context Protocol (MCP), developed by Anthropic, is an advanced protocol that defines how to connect Large Language Models (LLMs) to external tools. It has quickly gained prominence for its ease of use and the benefits it brings to the use of AI. In this article, we will cover some of the possible security risks related to MCP and how to mitigate them.
How MCP Works
MCP does not connect LLMs directly to tools. The MCP client accesses the LLM, and the MCP server accesses the tools. An MCP client has access to one or more MCP servers, and users can connect multiple servers to a single MCP client.
Here's how a typical exchange between the MCP client and server occurs:
- The user requests a task from the MCP client.
- The MCP client has information about which tools each MCP server implements or has access to.
- The client sends the user's request with information from the MCP servers to an LLM, which responds by indicating the appropriate tool and the parameters to be used.
- The MCP client sends the information about the tools and parameters to the MCP server.
- After completing the task, the MCP server sends the response to the MCP client, which forwards it to the LLM. The LLM then generates the final response for the user.
- The MCP client displays the response to the user.
MCP servers can run both locally and remotely, and the security risks change depending on the execution mode. We call "local MCP servers" those executed on a host under our control, which typically perform tasks by executing operating system commands or custom code locally. "Remote MCP servers" are those run only remotely by third parties.
Security Risks and Mitigations
Below is an overview of some of the security risks of MCP and the recommended mitigation measures.
Confused Deputy Problem
Attackers can exploit MCP proxy servers that connect to third-party APIs, creating "confused deputy" vulnerabilities. This attack allows malicious clients to obtain authorization codes without proper user consent.
The ideal is that the MCP server performs the action on behalf of the user and with their permission. However, this is not guaranteed and depends on the implementation of the MCP server. If not implemented correctly, a user may end up accessing resources that should not be available to them, violating the Principle of Least Privilege (PoLP).
Attack Flow
A confused deputy attack is possible when an MCP proxy server uses a static client ID with a third-party authorization server, allows dynamic client registration, and the third-party server sets a consent cookie.
Normal Flow (with User Consent):
sequenceDiagram
participant UA as User-Agent (Browser)
participant MC as MCP Client
participant M as MCP Proxy Server
participant TAS as Third-Party Authorization Server
Note over UA,M: Initial Auth flow completed
M->>UA: Redirect to third party authorization server
UA->>TAS: Authorization request (client_id: mcp-proxy)
TAS->>UA: Authorization consent screen
UA->>TAS: Approve
TAS->>UA: Set consent cookie for client ID: mcp-proxy
TAS->>UA: 3P Authorization code + redirect
UA->>M: 3P Authorization code
M->>UA: Redirect to MCP Client with MCP authorization code
Malicious Flow (Bypassing User Consent):
sequenceDiagram
participant UA as User-Agent (Browser)
participant M as MCP Proxy Server
participant TAS as Third-Party Authorization Server
participant A as Attacker
A->>M: Dynamically register malicious client, redirect_uri: attacker.com
A->>UA: Sends malicious link
UA->>TAS: Authorization request (client_id: mcp-proxy) + consent cookie
rect rgba(255, 17, 0, 0.67)
TAS->>TAS: Cookie present, consent skipped
end
TAS->>UA: 3P Authorization code + redirect
UA->>M: 3P Authorization code
M->>UA: Redirect to attacker.com with MCP Authorization code
UA->>A: MCP Authorization code delivered to attacker.com
A->>M: Attacker impersonates user to MCP server
Mitigation
To prevent confused deputy attacks, MCP proxy servers MUST implement per-client consent before the third-party authorization flow.
- Per-Client Consent Storage: Maintain a registry of approved
client_idvalues per user and check this registry before initiating the third-party authorization flow. - Consent UI Requirements: The MCP-level consent page must clearly identify the requesting client, display the scopes being requested, show the
redirect_uri, and implement CSRF protection. - Redirect URI Validation: Validate that the
redirect_uriin authorization requests exactly matches the registered URI. - OAuth State Parameter Validation: Use a cryptographically secure
stateparameter to prevent CSRF and ensure the consent approval is enforced at the callback.
Token Passthrough
"Token passthrough" is an anti-pattern where an MCP server accepts tokens from an client without validating that the tokens were properly issued to the MCP server and passes them to a downstream API. This is explicitly forbidden as it can lead to security control circumvention, audit trail issues, and trust boundary problems.
Mitigation
MCP servers MUST NOT accept any tokens that were not explicitly issued for the MCP server.
Server-Side Request Forgery (SSRF)
An attacker can induce an MCP client to make HTTP requests to unintended destinations, potentially accessing internal network resources or cloud metadata endpoints. This can happen during OAuth metadata discovery, where URLs are fetched from sources that could be controlled by a malicious MCP server.
Mitigation
MCP clients deployed to a server MUST implement appropriate SSRF mitigations:
- Enforce HTTPS: Require HTTPS for all OAuth-related URLs in production.
- Block Private IP Ranges: Block requests to private and reserved IP address ranges (e.g.,
10.0.0.0/8,169.254.0.0/16). - Validate Redirect Targets: Apply the same URL validation to redirect targets.
- Use Egress Proxies: Route OAuth discovery requests through a proxy that enforces network policies.
Unauthorized Command Execution & Prompt Injection
Local MCP servers can execute any code. Depending on implementation, command execution may be vulnerable to injection attacks. Additionally, a malicious prompt from a third party could be used to leak private information or execute unintended actions.
For example, a vulnerable MCP server might not properly sanitize inputs:
def dispatch_user_alert(self, notification_info: Dict[str, Any], summary_msg: str) -> bool:
"""Sends system alert to user desktop"""
notify_config = self.user_prefs["alert_settings"]
try:
alert_title = f"{notification_info['title']} - {notification_info['severity']}"
if sys.platform == "linux":
# Vulnerable to command injection via alert_title
subprocess.call(["notify-send", alert_title])
return True
Mitigation
- Always validate and sanitize data before using it as arguments in functions that execute commands.
- Run local MCP servers in a sandbox to limit their access to only what is necessary.
- Actions taken by MCP servers should always be confirmed by users or properly restricted to reduce risk to an acceptable level.
Supply Chain Risks
Since MCP servers are executable code, users must only use servers they trust. Components should be signed by the developer, developed in secure pipelines (using SAST and SCA), and scanned for malware.
Conclusion
MCP has generated interest in manipulating tools with natural language and better understanding how we communicate with users, LLMs, and tools. However, we must consider the security risks associated with advancing automation and adopting AI agents. As with any new technology, when using MCP, companies must assess their security risks and implement appropriate controls to fully leverage the benefits of the technology.

