-
Notifications
You must be signed in to change notification settings - Fork 5
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #68 from CoinFabrik/67-add-remaining-detector-and-…
…vulnerability-documentation 67 add remaining detector and vulnerability documentation
- Loading branch information
Showing
6 changed files
with
215 additions
and
1 deletion.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
# Panic error | ||
|
||
### What it does | ||
|
||
The `panic!` macro is used to stop execution when a condition is not met. | ||
This is useful for testing and prototyping, but should be avoided in production code. | ||
|
||
### Why is this bad? | ||
|
||
The usage of `panic!` is not recommended because it will stop the execution of the caller contract. | ||
|
||
### Known problems | ||
|
||
While this linter detects explicit calls to `panic!`, there are some ways to raise a panic such as `unwrap()` or `expect()`. | ||
|
||
### Example | ||
|
||
```rust | ||
pub fn add(env: Env, value: u32) -> u32 { | ||
let storage = env.storage().instance(); | ||
let mut count: u32 = storage.get(&COUNTER).unwrap_or(0); | ||
match count.checked_add(value) { | ||
Some(value) => count = value, | ||
None => panic!("Overflow error"), | ||
} | ||
storage.set(&COUNTER, &count); | ||
storage.extend_ttl(100, 100); | ||
count | ||
} | ||
``` | ||
|
||
Use instead: | ||
|
||
```rust | ||
pub fn add(env: Env, value: u32) -> Result<u32, Error> { | ||
let storage = env.storage().instance(); | ||
let mut count: u32 = storage.get(&COUNTER).unwrap_or(0); | ||
match count.checked_add(value) { | ||
Some(value) => count = value, | ||
None => return Err(Error::OverflowError), | ||
} | ||
storage.set(&COUNTER, &count); | ||
storage.extend_ttl(100, 100); | ||
Ok(count) | ||
} | ||
``` | ||
|
||
### Implementation | ||
|
||
The detector's implementation can be found at [this link](https://github.com/CoinFabrik/scout-soroban/tree/main/detectors/avoid-panic-error). |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
# Avoid unsafe block | ||
|
||
### What it does | ||
|
||
Checks for usage of `unsafe` blocks. | ||
|
||
### Why is this bad? | ||
|
||
`unsafe` blocks should not be used unless absolutely necessary. The use of unsafe blocks in Rust is discouraged because they bypass Rust's memory safety checks, potentially leading to issues like undefined behavior and security vulnerabilities. | ||
|
||
### Example | ||
|
||
```rust | ||
pub fn unsafe_function(n: u64) -> u64 { | ||
unsafe { | ||
let mut i = n as f64; | ||
let mut y = i.to_bits(); | ||
y = 0x5fe6ec85e7de30da - (y >> 1); | ||
i = f64::from_bits(y); | ||
i *= 1.5 - 0.5 * n as f64 * i * i; | ||
i *= 1.5 - 0.5 * n as f64 * i * i; | ||
|
||
let result_ptr: *mut f64 = &mut i; | ||
let result = *result_ptr; | ||
|
||
result.to_bits() | ||
} | ||
} | ||
``` | ||
|
||
Use instead: | ||
|
||
```rust | ||
pub fn unsafe_function(n: u64) -> u64 { | ||
let mut i = n as f64; | ||
let mut y = i.to_bits(); | ||
y = 0x5fe6ec85e7de30da - (y >> 1); | ||
i = f64::from_bits(y); | ||
i *= 1.5 - 0.5 * n as f64 * i * i; | ||
i *= 1.5 - 0.5 * n as f64 * i * i; | ||
result.to_bits() | ||
} | ||
``` | ||
|
||
### Implementation | ||
|
||
The detector's implementation can be found at [this link](https://github.com/CoinFabrik/scout-soroban/tree/main/detectors/avoid-unsafe-block). |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,43 @@ | ||
# DoS unbounded operation | ||
|
||
### What it does | ||
|
||
This detector checks that when using for or while loops, their conditions limit the execution to a constant number of iterations. | ||
|
||
### Why is this bad? | ||
|
||
If the number of iterations is not limited to a specific range, it could potentially cause out of gas exceptions. | ||
|
||
### Known problems | ||
|
||
False positives are to be expected when using variables that can only be set using controlled flows that limit the values within acceptable ranges. | ||
|
||
### Example | ||
|
||
```rust | ||
pub fn unrestricted_loop(for_loop_count: u64) -> u64 { | ||
let mut count = 0; | ||
for i in 0..for_loop_count { | ||
count += i; | ||
} | ||
count | ||
} | ||
``` | ||
|
||
Use instead: | ||
|
||
```rust | ||
const FIXED_COUNT: u64 = 1000; | ||
|
||
pub fn restricted_loop_with_const() -> u64 { | ||
let mut sum = 0; | ||
for i in 0..FIXED_COUNT { | ||
sum += i; | ||
} | ||
sum | ||
} | ||
``` | ||
|
||
### Implementation | ||
|
||
The detector's implementation can be found at [this link](https://github.com/CoinFabrik/scout-soroban/tree/main/detectors/dos-unbounded-operation). |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
# Soroban version | ||
|
||
### What it does | ||
|
||
Warns you if you are using an old version of Soroban in the `Cargo.toml`. | ||
|
||
### Why is this bad? | ||
|
||
Using an old version of Soroban can be dangerous, as it may have bugs or security issues. | ||
|
||
### Example | ||
|
||
```toml | ||
[dependencies] | ||
soroban-sdk = { version = "=20.0.0" } | ||
|
||
[dev_dependencies] | ||
soroban-sdk = { version = "=20.0.0", features = ["testutils"] } | ||
``` | ||
|
||
Instead, use the latest available version in the `Cargo.toml`. | ||
|
||
### Implementation | ||
|
||
The detector's implementation can be found at [this link](https://github.com/CoinFabrik/scout-soroban/tree/main/detectors/soroban-version). |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters