ishish.io
ishish.io

What is now proved
was once, only imagin'd

- William Blake

Threat model for blockchain - part 2: Service provider perspective

This entry is part of a series of blog entries in which I attempt to build a comprehensive threat model for the blockchain ecosystem. Check out the introductory entry.

When it comes to services on blockchain, we can view them similarly to regular services in terms of functions  and threats. Service providers, as in off-chain applications, are trying to make a coin by providing useful products and services to their users. So we're looking for example at:

- Fungible and non-fungible token contracts
- Token exchanges
- On-chain wallets
- Lending smart contracts
- DAOs
- many other types of service.

I will also refer to services as smart contracts.

In case of service developers, besides looking at the threats related to the service alone, it's also worthwhile to look at the development process (Software Development Life Cycle). I will do this in a separate blog entry because I think that due to numerous differences it makes sense to separate these two aspects.

Although risk analysis related to the exposure of assets that remain under control of service provider is a more general task than threat modelling, I feel that I should mention as a part of this entry's introduction that in case of on-chain applications risks can be considerably higher than in case of off-chain equivalents. The reasons for this include:
- sensitivity of assets under control
- volume of assets and transactions
- exposure in terms of code and data visibility
- unknowns that are related to the use of emerging technologies

For this reason I think that potential service providers should exhibit due diligence and due care for safeguarding assets under their control and understanding threat model of their perspective is a key aspect of this.

All right, let's explore the threats. As usual, I will rely on the STRIDE methodology.

(S)poofing

Many functions of the services rely on user's identity. For example, balances in token contracts are assigned to specific accounts representing individual users. Method for verifying that the user calling the function of smart contract is who she claims she is called authentication. In off-chain services usually authentication controls are being included in the application's code and supplied user's credentials are verified against the user database.

In case of on-chain services authentication is provided by the underlying blockchain layers. In order to send out transaction, each user needs to establish her ECC keypair. The public key in the keypair is used to derive address which is the user's identifier. Each transaction on the blockchain has two parties of which each is identified by her address. Therefore, the user is already in the possession of her credentials and the same credentials are being re-used by all services on-chain for purposes of authentication, no need for the user database.

So, the spoofing-related threats for service-providers are being mitigated by the security controls in the underlying layers of blockchain that provide implementation of authentication methods based on ECC cryptosystem. And isn't much code that might be vulnerable in the smart contract itself, therefore vulnerabilities in this specific area are not a significant problem. One related issue might be tampering with user-related data, but I will delve into this in the next section.

There is one more very interesting threat related to spoofing - impersonating contracts. Some contract, due to their functionality, can be tricked into making calls that they were not supposed to do in the course of executing legitimate business process. This type of vulnerability can be used to spoof the contract and potentially abuse the trust placed in the contract by other users/contracts to achieve malicious goals. One real-world case study of exploitation of such vulnerability was the Poly Network hack.

For avoiding this type of vulnerabilities and mitigate spoofing threats, security code review is a primary security control.

Another aspect that remains important is verification of the service's contract address by a potential user, but this belongs to the user's perspective.

(T)ampering

Tampering with internal service state is a serious problem in off-chain applications. There are many ways to do it - to include malicious code in a workload, to modify data in the database (compromising its integrity), to name a few. This problem is partly solved with the underlying blockchain layers that ensure code immutability. This means that a smart contract, once deployed, cannot be altered. It's a huge help. Think about all of those security controls that are being employed off-chain (and their costs) - code access control, code reviews, signing artifacts, access control to workloads, artifact integrity verification, backups, etc.. Thanks to code immutability, it all goes away.

Well, almost. While code is immutable, the service data remains mutable. And data can POINT to code. And sometimes in smart contracts it does. This is a way to introduce upgradeability to an environment build on immutable code.

In blockchain smart contract there still exists issue of vulnerabilities. If a vulnerability or weakness has been introduced into service and is discovered, its important to manage the vulnerability mitigation process. If upgradeability is implemented, the developers can fix the code, deploy it to blockchain (rendering it immutable) and redirect the code pointer. Therefore, in some situations by redirecting pointers to contracts or functions, a malicious actor can defacto modify functions. But the attack surface is much smaller than in case of the off-chain equivalents.

Data tampering is another thing and if there's a major source of service provider's headaches, that's it. Integrity of smart contract's data is paramount to its security. For example, if someone was able to increase its balance of ERC20 tokens, it defeats the whole urpose of the service, doesn't it? First security control that can be used to protect the data integroty is access control. It can be implemented with the use of modifiers that verify if caller is authorized to modify the data and with controlling the visibility of data variables (e.g., private data can only be accessed by the contract itself).

But many security controls can contain vulnerabilities that will limit their effectiveness. For example, if you make mistakes while implementing upgradeability using a proxy contract its possible that the variable controlling smart contract's ownership can be overwritten. Therefore, a malicious actor can defeat the security control and access functions and data that she's not supposed to (e.g., mint a large quantity of tokens to her account).

An extreme case of tampering is contract destruction with the SELFDESTRUCT opcode.

The most important controls for mitigating the threat of data tampering would be:
- access control
- applying code and security patterns
- functionality tests before deployment
- security review of code before deployment
- properly implemented upgradeability

I need to mention here that upgradeability in itself is a controversial topic. I will be discussing this tool as a security control in one of my future entries.

(R)epudiation

When we're selling a commodity or service, we want to make sure that we'll receive the payment. On the other side of the deal, our client wants to be certain that she will receive her product / service that she paid for. The opposite - not fulfilling one's part of the deal - is called repudiation. Elimination of a possibility of repudiation is called non-repudiation.

In off-chain services this mutual promise is entirely dependent on trust. A customer usually only performs purchases via trusted sites, stores, payment processors. The service/product provider only sends out the package once the payment has been confirmed by a trusted third party.

One of the superpowers of blockchain is that it eliminates the need for trust. The trust is replaced by a complex Byzantine-Fault Tolerant (BFT) consensus protocol that introduced non-repudiation. It means that the parties of the transaction are cryptographically identifiable and a transaction recorded on the blockchain cannot be altered once its finalized. In short, if the transaction is made, it cannot be unmade. If a customer spends a cryptocoin, this coin cannot by spent by her again (double-spending protection).

Again, this security control is provided by the underlying blockchain layers and an intricate web of algorithms that enforce so called crypto-economic security. One thing that needs to be considered by the service provider and a customer alike is the transaction finality. A transaction is considered final if it's included in a finalized block. Finalized block is extremely difficult and costly to alter.

(I)nformation disclosure

Potential for unintentional information disclosure is ia significant threat in case of blockchain solutions. Often data leaks are caused by incorrent use of the blockchain technology. In public, permissionless networks such as Bitcoin or Ethereum blockchain data is globally available. This is a design choice for these networks, without it achieving some of the goals (transparency, trust, decentralization) wouldn't be possible.

From the service provider's perspective it's extremely important to understand how transaction data is handled by specific blockchain solution before submitting it to the network. Especially when data contains:
- intellectual property
- personal data
- banking secrets
- other secrets

Service providers should use appropriate functions to protect sensitive data. Possible solutions include:
- using crypto commitments for concealing data
- using ZK proofs
- using specialized L1 or L2 solutions such as Hyperledger Fabric channels or state-channels.

One significant specific information disclusure threat is related to the compromise of key/wallet confidentiality. Service providers can be affected by this threat but it's discussed in the user perspective as I think it belongs there.

(D)enial of Service

Denial of Service (DoS) occurs when the service is not available for use for a legitimate user. This undesirable service state can be triggered by a variety of things:
- overwhelming the service with large volume of malicious traffic in order to exhausting computational resources
- maliciously triggering an error conditions that put the service in an undefined state
- economic DoS - exhausting financial resources in case of specific pricing models (e.g. pay per request)

Threats related to DoS are in main part mitigated by the underlying layers of blockchain. They are relying on the strength of P2P networks, decentralization and economic deterrents (gas market). These are interesting mitigation controls and I will delve into them in subsequent posts. But for now, let's focus on aspects of DoS that belong to the service provider perspective.

Important consideration here should be the gas consumption during function executions. Especially if the following execution flow constructions are being used:
- recurrent calls
- loops
- functions with imposed gas limits (e.g. when triggered via send or transfer methods)
and the conditions that control these. If a potential attacker can gain control of variables controlling loops or recurrent calls, she can create conditions in which computational complexity will cross the allowed threshold and will render the function un-callable (potentially leaving the contract unusable). There also exists a possibility of involuntary lockout of a contract during legitimate operation.

The basic security control that can help mitigate this threat is of course code review with focus on any execution control flow constructions that might enable DoS conditiond. Another control can be upgradeability but in many cases it might prove uneffective. If state variables controling flow are stored in the proxy (which is usually the case) the lockout might prove impossible to fix even with an implementation code upgrade.

(E)levation of privilege

Elevation of privilege happens when an actor can maliciously assume a role or privileges higher than the ones she has. In case of off-chain services this is usually done in the so called "lateral movement" stage of an operation. Once an attacker gains a foothold in the infrastructure, she is looking for ways of gaining additional privileges. She can e.g. try and steal workload credentials on a compromised EC2 machine use them to authorize calls.

In blockchain the concept of privileges is implemented on the service level. That's becasuse privileges definitions are closely connected to the business processes and individual roles that participate in the processes. Role should be assigned sufficient privileges to execute her part of the process and not more (principle of least privilege). This means, only the service provider, knowing her business processes and required roles, is able to define a set of privileges required and assign it to roles. Fortunately, there exist code patterns that can be re-used to implement RBAC once privileges are defined.

In the blockchain world, elevation of provilege is usually done via data tampering (see the (T)ampering section) of variables related to access control or by more general attempts at spoofing. A robust and secure Role-based Access Control (RBAC) system should be sufficient to mitigate these threats, ideally relying on verified, battle-tested code patterns.

Threat materialization and incident response

When the worst happens and a threat belonging to the service provider perspective materializes (becomes an incident), it's her responsibility to detect it and mitigate it. Incident detection and mitigation process can be quite complex. There are numerous attempts at regulating it (see e.g. NIST 800-61) but the basics are relatively simple.

Proper response to incident by the service provider includes:
1. preparation
2. detection
3. containment, erradication & recovery
4. post-icident activity

Let's briefly go over these steps:

Preparation

Preparation means implementing the security controls that are supposed to mitigate the threats. This is pre-incident activity and it means that service provider should take due care of the threats and have the controls implemented before the production use. It also means that the remaining steps of the incident response are prepared and ready for use.

Detection

Detection means all of the organizational and technical measures that aim at identifying successful (optionaly unsuccessful as well) attempts at attacking the service. Here logging, monitoring and alerting play a crucial role. Many details about the contract operation can hint at an anomaly or an incident, to name a few: abnormal fluctuations in balance, abnormal volume of transactions, abnormal percentage of failed transactions, transactions with denylisted parties, etc..

Containment, erradication & recovery

At this step of incident response, tools and procedures is the king. Once the incident materializes usually emotions start kicking in. It's very easy to make a mistake, an omission, to succumb to emotions such as fear that limit the ability to use reasoning. In this context, well-defined and tested procedures help incident response teams to face dire situations wisely.

Procedures should allow classification of an incident according to the estimated damages and functional class. They should point to specific tools and security controls and the rules of using them such as:
- pausability
- upgradeability
- escape hatches
- etc.

Post-incident activity

This is mostly investigations and learning with the primary goal of avoiding threat materialization in the future. Lessons extracted from this step should be applied in another cycle of the incident response lifecycle in the preparation step - implementing better controls, correcting incident response procedures, etc.

Summary

The service provider's perspective of the overall blockchain threat model is very interesting. Service provider occupies the space between the client/user and providers of underlying blockchain providers, be it L1 or L2 solutions. In my opinion, based on the threat analysis, service providers in the blockchain world are in much more comfortable position that in case of off-chain. While the exposure is much higher in terms of visibility and interconnections (almost everything on-chain can be considered an attack surface from the OPSEC perspective), they have a variety of security controls provided by the underlying blockchain layers, including:
- user authentication methods based on robust ECC-based cryptosystem
- protection of code and data integrity
- transactions non-repudiation
- Denial of Service resillience

These controls are included as part of the blockchain offer. It's a considerable package, given the cost of operating equivalent controls in off-chain infrastructures. However, there still exist some threats that are common to most on-chain applications that need to be properly mitigated by the service provider. It can be done with the use of the following security controls:
- applying verified code patterns
- code reviews
- contract interactions monitoring, incident detection and mitigation
- robust RBAC access control with well-defined privileges and assignable roles

In my subseqnent posts I will delve into details of selected threats and threat mitigation controls. Stay tuned!

Also, feel free to reach out to me to share any feedback!

ishish.io Copyright 2024