-
Notifications
You must be signed in to change notification settings - Fork 57
/
checklist.json
3422 lines (3422 loc) · 239 KB
/
checklist.json
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
[
{
"category": "Attacker's Mindset",
"description": "General check items for main attack types.",
"data": [
{
"category": "Denial-Of-Service(DOS) Attack",
"description": "Attackers overload a system, making it unavailable to legitimate users, often by exploiting design vulnerabilities or resource limitations.",
"data": [
{
"id": "SOL-AM-DOSA-1",
"question": "Is the withdrawal pattern followed to prevent denial of service?",
"description": "To prevent denial of service attacks during withdrawals, it's critical to follow the withdrawal pattern best practices - pull based approach.",
"remediation": "Implement withdrawal pattern best practices to ensure that contract behavior remains predictable and robust against denial of service attacks.",
"references": [
"https://solodit.xyz/issues/m-06-denial-of-service-contract-owner-could-block-users-from-withdrawing-their-strike-code4rena-putty-putty-contest-git"
],
"tags": []
},
{
"id": "SOL-AM-DOSA-2",
"question": "Is there a minimum transaction amount enforced?",
"description": "Enforcing a minimum transaction amount can prevent attackers from clogging the network with zero amount or dust transactions.",
"remediation": "Disallow transactions below a certain threshold to maintain efficiency and prevent denial of service through dust spamming.",
"references": [
"https://solodit.xyz/issues/h-02-denial-of-service-code4rena-hubble-hubble-contest-git"
],
"tags": []
},
{
"id": "SOL-AM-DOSA-3",
"question": "How does the protocol handle tokens with blacklisting functionality?",
"description": "Tokens with blacklisting capabilities, such as USDC, can pose unique risks and challenges to protocols.",
"remediation": "Account for the possibility of blacklisting within token protocols to ensure continued functionality even if certain addresses are blacklisted.",
"references": [],
"tags": []
},
{
"id": "SOL-AM-DOSA-4",
"question": "Can forcing the protocol to process a queue lead to DOS?",
"description": "Forcing protocols to process queues, like a queue of dust withdrawals, can be exploited to cause a denial of service.",
"remediation": "Design queue processing in a manner that is resilient to spam and cannot be exploited to cause denial of service.",
"references": [],
"tags": []
},
{
"id": "SOL-AM-DOSA-5",
"question": "What happens with low decimal tokens that might cause DOS?",
"description": "Tokens with low decimals can present issues where the transaction process fails due to rounding to zero amounts.",
"remediation": "Implement logic to handle low decimal tokens in a way that prevents the transaction process from breaking due to insufficient token amounts.",
"references": [
"https://solodit.xyz/issues/potential-funds-locked-due-low-token-decimal-and-long-stream-duration-spearbit-locke-pdf"
],
"tags": []
},
{
"id": "SOL-AM-DOSA-6",
"question": "Does the protocol handle external contract interactions safely?",
"description": "Protocols must handle interactions with external contracts in a way that does not compromise their functionality if external dependencies fail.",
"remediation": "Ensure robust handling of external contract interactions to maintain protocol integrity regardless of external contract performance.",
"references": [
"https://solodit.xyz/issues/m-09-unhandled-chainlink-revert-would-lock-all-price-oracle-access-code4rena-juicebox-juicebox-v2-contest-git"
],
"tags": []
}
]
},
{
"category": "Donation Attack",
"description": "An attacker sends some amount of cryptocurrency to a contract and makes the protocol accounting reaches to an unexpected state.",
"data": [
{
"id": "SOL-AM-DA-1",
"question": "Does the protocol rely on `balance` or `balanceOf` instead of internal accounting?",
"description": "Attackers can manipulate the accounting by donating tokens.",
"remediation": "Implement internal accounting instead of relying on `balanceOf` natively.",
"references": [
"https://solodit.xyz/issues/h-02-first-depositor-can-break-minting-of-shares-code4rena-prepo-prepo-contest-git"
],
"tags": []
}
]
},
{
"category": "Front-running Attack",
"description": "Attackers watch pending transactions and then push their own transaction with a higher gas fee, ensuring it's executed before the targeted transaction.",
"data": [
{
"id": "SOL-AM-FrA-1",
"question": "Are there measures in place to prevent frontrunning vulnerabilities in get-or-create patterns?",
"description": "Get-or-create pattern functionality is prone to frontrunning attacks.",
"remediation": "Ensure the frontrunning does not cause user loss or unexpected problems.",
"references": [],
"tags": []
},
{
"id": "SOL-AM-FrA-2",
"question": "Are two-transaction actions designed to be safe from frontrunning?",
"description": "Actions that require two separate transactions may be at risk of frontrunning, where an attacker can intervene between the two calls.",
"remediation": "Ensure critical actions that are split across multiple transactions cannot be interfered with by attackers. This can involve checks or locks between the transactions.",
"references": [
"https://github.com/sherlock-audit/2022-11-isomorph-judging/issues/47"
],
"tags": []
},
{
"id": "SOL-AM-FrA-3",
"question": "Can users maliciously cause others' transactions to revert by preempting with dust?",
"description": "Attackers may cause legitimate transactions to fail by front-running with transactions of negligible amounts.",
"remediation": "Implement checks to prevent transactions with non-material amounts from affecting the contract's state or execution flow.",
"references": [
"https://solodit.xyz/issues/m-12-attacker-can-grift-syndicate-staking-by-staking-a-small-amount-code4rena-stakehouse-protocol-lsd-network-stakehouse-contest-git"
],
"tags": []
},
{
"id": "SOL-AM-FrA-4",
"question": "Does the protocol need a commit-reveal scheme?",
"description": "Without a commit-reveal scheme, actions such as votes or bids are exposed in the mempool before they are mined, allowing adversaries to see and potentially act on this information. The commit-reveal pattern maintains confidentiality until all commitments are made.",
"remediation": "Implement a commit-reveal scheme where users first commit a hash of their intended action and then reveal the actual action after the commitment phase is over. This protects against front-running and provides a fairer process.",
"references": [],
"tags": []
}
]
},
{
"category": "Griefing Attack",
"description": "Malicious actors intentionally cause harm to a system, often without direct profit for themselves, just to disrupt its operations or users.",
"data": [
{
"id": "SOL-AM-GA-1",
"question": "Is there an external function that relies on states that can be changed by others?",
"description": "Malicious actors can prevent normal user transactions by making a slight change on the on-chain states. More problematic on L2 chains where tx fee is low.",
"remediation": "Ensure normal user actions especially important actions like withdrawal/repayment are not disturbed by other actors.",
"references": [
"https://solodit.xyz/issues/m-10-griefing-attack-to-block-withdraws-code4rena-mochi-mochi-contest-git"
],
"tags": []
}
]
},
{
"category": "Miner Attack",
"description": "Miners, who validate and add transactions to the blockchain, manipulate block attributes like hash or timestamp to influence contract execution or outcomes.",
"data": [
{
"id": "SOL-AM-MA-1",
"question": "Is `block.timestamp` used judiciously, especially for longer intervals?",
"description": "`block.timestamp` can be manipulated by miners to a small extent, so relying on it for precise timing might be risky.",
"remediation": "Use `block.timestamp` only where a slight inaccuracy is acceptable, such as for longer intervals.",
"references": [],
"tags": [
"Miner Attack"
]
}
]
},
{
"category": "Price Manipulation Attack",
"description": "Malicious actors intentionally alter the price of assets on decentralized exchanges, usually to exploit dependent contracts or trades.",
"data": [
{
"id": "SOL-AM-PMA-1",
"question": "How does the protocol get the price of assets?",
"description": "Price, or rates between assets more generally, can be manipulated if it is derived from the ratio of balance. Flash loan and donation are the well-known attack vectors used to manipulate the prices.",
"remediation": "Use the Chainlink oracles for the asset prices and implement internal accounting instead of relying on `balanceOf`.",
"references": [
"https://solodit.xyz/issues/h-05-flash-loan-price-manipulation-in-purchasepyroflan-code4rena-behodler-behodler-contest-git",
"https://solodit.xyz/issues/h-05-underlying-assets-stealing-in-autopxgmx-and-autopxglp-via-share-price-manipulation-code4rena-redacted-cartel-redacted-cartel-contest-git",
"https://solodit.xyz/issues/h-02-use-of-slot0-to-get-sqrtpricelimitx96-can-lead-to-price-manipulation-code4rena-maia-dao-ecosystem-maia-dao-ecosystem-git"
],
"tags": []
}
]
},
{
"category": "Reentrancy Attack",
"description": "An attacker exploits a contract's logic to repeatedly call into a function before the previous invocation is complete, potentially draining funds.",
"data": [
{
"id": "SOL-AM-ReentrancyAttack-1",
"question": "Is there a view function that can return a stale value during interactions?",
"description": "Read-only reentrancy. The read-only reentrancy is a reentrancy scenario where a view function is reentered, which in most cases is unguarded as it does not modify the contract's state. However, if the state is inconsistent, wrong values could be reported. Other protocols relying on a return value can be tricked into reading the wrong state to perform unwanted actions.",
"remediation": "Extend the reentrancy guard to the view functions as well.",
"references": [
"https://medium.com/@zokyo.io/read-only-reentrancy-attacks-understanding-the-threat-to-your-smart-contracts-99444c0a7334",
"https://solodit.xyz/issues/m-03-read-only-reentrancy-is-possible-code4rena-angle-protocol-angle-protocol-invitational-git",
"https://solodit.xyz/issues/h-13-balancerpairoracle-can-be-manipulated-using-read-only-reentrancy-sherlock-none-blueberry-update-git"
],
"tags": [
"Reentrancy Attack"
]
},
{
"id": "SOL-AM-ReentrancyAttack-2",
"question": "Is there any state change after interaction to an external contract?",
"description": "Untrusted external contract calls could callback leading to unexpected results such as multiple withdrawals or out-of-order events.",
"remediation": "Use check-effects-interactions pattern or reentrancy guards.",
"references": [
"https://www.geeksforgeeks.org/reentrancy-attack-in-smart-contracts/",
"https://solodit.xyz/issues/m-09-malicious-royalty-recipient-can-steal-excess-eth-from-buy-orders-code4rena-caviar-caviar-private-pools-git",
"https://solodit.xyz/issues/h-01-re-entrancy-in-settleauction-allow-stealing-all-funds-code4rena-kuiper-kuiper-contest-git"
],
"tags": [
"Reentrancy Attack"
]
}
]
},
{
"category": "Replay Attack",
"description": "Attackers resend or duplicate valid data/signature transmissions to deceive or impersonate another entity.",
"data": [
{
"id": "SOL-AM-ReplayAttack-1",
"question": "Are there protections against replay attacks for failed transactions?",
"description": "Failed transactions can be susceptible to replay attacks if not properly protected.",
"remediation": "Implement nonce-based or other mechanisms to ensure that each transaction can only be executed once, preventing replay attacks.",
"references": [
"https://github.com/code-423n4/2022-03-rolla-findings/issues/45"
],
"tags": []
},
{
"id": "SOL-AM-ReplayAttack-2",
"question": "Is there protection against replaying signatures on different chains?",
"description": "Signatures valid on one chain may be replayed on another, leading to potential security breaches.",
"remediation": "Use chain-specific parameters or domain separators to ensure signatures are only valid on the intended chain.",
"references": [
"https://github.com/sherlock-audit/2022-09-harpie-judging/blob/main/004-M/004-m.md"
],
"tags": []
}
]
},
{
"category": "Rug Pull",
"description": "Developers or initial project backers abruptly withdraw their funds from a decentralized project or application, often leaving other investors at a loss.",
"data": [
{
"id": "SOL-AM-RP-1",
"question": "Can the admin of the protocol pull assets from the protocol?",
"description": "Some protocols grant an admin with a privilege of pulling assets directly from the protocol. In general, if there is an actor that can affect the user funds directly it must be reported.",
"remediation": "Allow access to only the relevant parts of protocol funds, e.g. by tracking fees internally. Forcing a timelock on the admin actions can be another mitigation.",
"references": [
"https://solodit.xyz/issues/m-06-centralisation-risk-admin-role-of-tokenmanagereth-can-rug-pull-all-eth-from-the-bridge-code4rena-skale-skale-contest-git"
],
"tags": []
}
]
},
{
"category": "Sandwich Attack",
"description": "Malicious actors identify a target transaction on the blockchain, and place their own before and after it, capitalizing on potentially advantageous order execution.",
"data": [
{
"id": "SOL-AM-SandwichAttack-1",
"question": "Does the protocol have an explicit slippage protection on user interactions?",
"description": "An attacker can monitor the mempool and puts two transactions before and after the user's transaction. For example, when an attacker spots a large trade, executes their own trade first to manipulate the price, and then profits by closing their position after the user's trade is executed.",
"remediation": "Allow users to specify the minimum output amount and revert the transaction if it is not satisfied.",
"references": [
"https://solodit.xyz/issues/h-12-sandwich-attack-to-accruepremiumandexpireprotections-sherlock-carapace-carapace-git",
"https://solodit.xyz/issues/h-1-adversary-can-sandwich-oracle-updates-to-exploit-vault-sherlock-olympus-olympus-update-git"
],
"tags": []
}
]
},
{
"category": "Sybil Attack",
"description": "A single adversary controls multiple nodes in a network, primarily to subvert its functionality or to gather more than their fair share of resources.",
"data": [
{
"id": "SOL-AM-SybilAttack-1",
"question": "Is there a mechanism depending on the number of users?",
"description": "It is very easy to trigger actions using a lot of alternative addresses on blockchain. Any quorum mechanism or utilization based rewarding system can be vulnerable to sybil attacks.",
"remediation": "Do not rely on the number of users in quorum design.",
"references": [
"https://solodit.xyz/issues/h-7-sybil-on-withdrawal-requests-can-allow-leverage-factor-manipulation-with-flashloans-sherlock-carapace-carapace-git",
"https://solodit.xyz/issues/routers-can-sybil-attack-the-sponsor-vault-to-drain-funds-spearbit-connext-pdf",
"https://solodit.xyz/issues/h-5-staker-rewards-can-be-gathered-with-maximal-multiplier-no-matter-how-borrowers-are-overdue-sherlock-union-finance-union-finance-git"
],
"tags": []
}
]
}
]
},
{
"category": "Basics",
"description": "",
"data": [
{
"category": "Access Control",
"description": "Vulnerabilities related to access control.",
"data": [
{
"id": "SOL-Basics-AC-1",
"question": "Did you clarify all the actors and their allowed interactions in the protocol?",
"description": "This is a general check item. Having a clear understanding of all relevant actors and interactions in the protocol is critical for security.",
"remediation": "List down all the actors and interactions and draw a diagram.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AC-2",
"question": "Are there functions lacking proper access controls?",
"description": "Access controls determine who can use certain functions of a contract. If these are missing or improperly implemented, it can expose the contract to unauthorized changes or withdrawals.",
"remediation": "Implement and rigorously test access controls like `onlyOwner` or role-based permissions to ensure only authorized users can access certain functions.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AC-3",
"question": "Do certain addresses require whitelisting?",
"description": "Whitelisting allows only a specific set of addresses to interact with the contract, offering an additional layer of security against malicious actors.",
"remediation": "Establish a whitelisting mechanism and ensure that only trusted addresses can execute sensitive or restricted operations.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AC-4",
"question": "Does the protocol allow transfer of privileges?",
"description": "Transfer of critical privileges must be done in two-step process. A two-step transfer process, usually involving a request followed by a confirmation, adds an extra layer of security against unintentional or malicious owner changes.",
"remediation": "Implement a two-step transfer mechanism that requires the new actor to accept the transfer, ensuring better security and intentional ownership changes.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AC-5",
"question": "What happens during the transfer of privileges?",
"description": "The protocol needs to work consistently and reasonably even during the transfer of privileges.",
"remediation": "Double check how the protocol works during the transfer of privileges.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AC-6",
"question": "Does the contract inherit others?",
"description": "If you do not override a parent contract's function explicitly, the parent's one will be exposed with its visibility and probably a wrong accessibiliy.",
"remediation": "Make sure you check the accessibility to the parent's external/public functions.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AC-7",
"question": "Does the contract use `tx.origin` in validation?",
"description": "Use of `tx.origin` for authorization may be abused by a malicious contract forwarding calls from the legitimate user. Use `msg.sender` instead. `require( tx.origin == msg.sender)` is a useful check to ensure that the `msg.sender` is an EOA(externally owned account).",
"remediation": "Make sure you know the difference of `tx.origin` and `msg.sender` and use properly.",
"references": [
"https://swcregistry.io/docs/SWC-115"
],
"tags": []
}
]
},
{
"category": "Array / Loop",
"description": "",
"data": [
{
"id": "SOL-Basics-AL-1",
"question": "What happens on the first and the last cycle of the iteration?",
"description": "Sometimes the first and last cycles have a different logic from others and there can be problems.",
"remediation": "Ensure the logic is correct for the first and the last cycles.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-4",
"question": "How does the protocol remove an item from an array?",
"description": "`delete` does not rearrange the array but just resets the element.",
"remediation": "Copy the last element to the index of the element to be removed and decrease the length of an array.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-5",
"question": "Does any function get an index of an array as an argument?",
"description": "If an array is supposed to be updated (removal in the middle), the indexes will change.",
"remediation": "Do not use an index of an array that is supposed to be updated as a parameter of a function.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-6",
"question": "Is the summing of variables done accurately compared to separate calculations?",
"description": "Direct calculation against a sum may yield different results than the sum of individual calculations, leading to precision issues.",
"remediation": "Ensure that summation logic is thoroughly tested and verified, especially when dealing with financial calculations to maintain accuracy.",
"references": [
"https://github.com/sherlock-audit/2022-11-isomorph-judging/issues/174"
],
"tags": []
},
{
"id": "SOL-Basics-AL-7",
"question": "Is it fine to have duplicate items in the array?",
"description": "In most cases, an array (especially an input array by users) is supposed to be unique.",
"remediation": "Add a validation to check the array is unique.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-8",
"question": "Is there any issue with the first and the last iteration?",
"description": "The first and the last iteration in loops can sometimes have edge cases that differ from other iterations, possibly leading to vulnerabilities.",
"remediation": "Always test the initial and the last iteration separately and ensure consistent behavior throughout all iterations.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-9",
"question": "Is there possibility of iteration of a huge array?",
"description": "Due to the block gas limit, there is a clear limitation in the amount of operation that can be handled in a transaction.",
"remediation": "Ensure the number of iterations is properly bounded.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-10",
"question": "Is there a potential for a Denial-of-Service (DoS) attack in the loop?",
"description": "Loops that contain external calls or are dependent on user-controlled input can be exploited to halt the contract's functions. (e.g. sending ETH to multiple users)",
"remediation": "Ensure a failure of a single iteration does not revert the whole operation.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-11",
"question": "Is `msg.value` used within a loop?",
"description": "`msg.value` is consistent for the whole transaction. If it is used in the for loop, it is likely there is a mistake in accounting.",
"remediation": "Avoid using `msg.value` inside loops. Refer to multi-call vulnerability.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-12",
"question": "Is there a loop to handle batch fund transfer?",
"description": "If there is a mechanism to transfer funds out based on some kind of shares, it is likely that there is a problem of 'dust' funds not handled correctly.",
"remediation": "Make sure the last transfer handles all residual.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-AL-13",
"question": "Is there a break or continue inside a loop?",
"description": "Sometimes developers overlook the edge cases that can happened due to the break or continue in the middle of the loop.",
"remediation": "Make sure the break or continue inside a loop does not lead to unexpected behaviors.",
"references": [],
"tags": []
}
]
},
{
"category": "Event",
"description": "",
"data": [
{
"id": "SOL-Basics-Event-1",
"question": "Does the protocol emit events on important state changes?",
"description": "Emitting events properly is important especially if the change is critical.",
"remediation": "Ensure to emit events in all important functions.",
"references": [],
"tags": []
}
]
},
{
"category": "Function",
"description": "",
"data": [
{
"id": "SOL-Basics-Function-1",
"question": "Are the inputs validated?",
"description": "Inputs to functions should be validated to prevent unexpected behavior.",
"remediation": "Ensure thorough validation. E.g. min/max for numeric values, start/end for dates, ownership of positions.",
"references": [
"https://solodit.xyz/issues/missing-owner-check-on-from-when-transferring-tokens-spearbit-clober-pdf",
"https://solodit.xyz/issues/m-13-bondbasesdasetdefaults-doesnt-validate-inputs-sherlock-bond-bond-protocol-git",
"https://solodit.xyz/issues/h-16-user-supplied-amm-pools-and-no-input-validation-allows-stealing-of-steth-protocol-fees-sherlock-swivel-illuminate-git"
],
"tags": []
},
{
"id": "SOL-Basics-Function-2",
"question": "Are the outputs validated?",
"description": "Outputs of functions should be validated to prevent unexpected behavior.",
"remediation": "Ensure the outputs are valid.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Function-3",
"question": "Can the function be front-run?",
"description": "Front-running can allow attackers to prioritize their transactions over others.",
"remediation": "Make sure there is no unexpected risk even if attackers front-run.",
"references": [
"https://solodit.xyz/issues/m-08-borrower-can-cause-a-dos-by-frontrunning-a-liquidation-and-repaying-as-low-as-1-wei-of-the-current-debt-code4rena-venus-protocol-venus-protocol-isolated-pools-git",
"https://solodit.xyz/issues/m-01-new-proposals-can-be-dosd-by-frontrunning-zachobront-none-optimismgovernormd-markdown_",
"https://solodit.xyz/issues/h-01-challenges-can-be-frontrun-with-de-leveraging-to-cause-lossses-for-challengers-code4rena-frankencoin-frankencoin-git"
],
"tags": []
},
{
"id": "SOL-Basics-Function-4",
"question": "Are the code comments coherent with the implementation?",
"description": "Misleading or outdated comments can result in misunderstood function behaviors.",
"remediation": "Keep comments updated and ensure they accurately describe the function logic.",
"references": [
"https://solodit.xyz/issues/m-08-wrong-comment-in-getfee-code4rena-yeti-finance-yeti-finance-contest-git",
"https://solodit.xyz/issues/m-8-wrong-change_collateral_delay-in-collateralbook-sherlock-isomorph-isomorph-git"
],
"tags": []
},
{
"id": "SOL-Basics-Function-5",
"question": "Can edge case inputs (0, max) result in unexpected behavior?",
"description": "Edge input values can lead to unexpected behavior.",
"remediation": "Make sure the function works as expected for the edge values.",
"references": [
"https://solodit.xyz/issues/lack-of-validation-openzeppelin-bancor-compounding-rewards-audit-markdown",
"https://solodit.xyz/issues/p1-m07-lack-of-input-validation-openzeppelin-eco-contracts-audit-markdown"
],
"tags": []
},
{
"id": "SOL-Basics-Function-6",
"question": "Does the function allow arbitrary user input?",
"description": "Implementing a function that accepts arbitrary user input and makes low-level calls based on this data introduces a significant security risk. Low-level calls in Solidity, such as call(), are powerful and can lead to unintended contract behavior if not used cautiously. With the ability for users to supply arbitrary data, they can potentially trigger unexpected paths in the contract logic, exploit reentrancy vulnerabilities, or even interact with other contracts in a malicious manner.",
"remediation": "Restrict the usage of low-level calls, especially when combined with arbitrary user input. Ensure that any data used in these calls is thoroughly validated and sanitized.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Function-7",
"question": "Should it be `external`/`public`?",
"description": "Ensure the visibility modifier is appropriate for the function's use, preventing unnecessary exposure.",
"remediation": "Limit function visibility to the strictest level possible (`private` or `internal`).",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Function-8",
"question": "Does this function need to be called by only EOA or only contracts?",
"description": "There are several edge cases regarding the caller checking mechanism, both for EOA and contracts.",
"remediation": "Ensure the correct access control is implemented according to the protocol's context. (read all the references)",
"references": [
"https://solodit.xyz/issues/m-15-onlyeoaex-modifier-that-ensures-call-is-from-eoa-might-not-hold-true-in-the-future-sherlock-blueberry-blueberry-git",
"https://solodit.xyz/issues/m-17-addressiscontract-is-not-a-reliable-way-of-checking-if-the-input-is-an-eoa-code4rena-stakehouse-protocol-lsd-network-stakehouse-contest-git"
],
"tags": []
},
{
"id": "SOL-Basics-Function-9",
"question": "Does this function need to be restricted for specific callers?",
"description": "Ensure that functions modifying contract state or accessing sensitive operations are access-controlled.",
"remediation": "Implement access control mechanisms like `onlyOwner` or custom modifiers.",
"references": [
"https://solodit.xyz/issues/h-8-lack-of-access-control-for-mintrebalancer-and-burnrebalancer-sherlock-none-ussd-autonomous-secure-dollar-git",
"https://solodit.xyz/issues/h-02-anyone-can-change-approvaldisapproval-threshold-for-any-action-using-llamarelativequorum-strategy-code4rena-llama-llama-git",
"https://solodit.xyz/issues/anyone-can-take-a-loan-out-on-behalf-of-any-collateral-holder-at-any-terms-spearbit-astaria-pdf"
],
"tags": []
}
]
},
{
"category": "Inheritance",
"description": "",
"data": [
{
"id": "SOL-Basics-Inheritance-1",
"question": "Is it necessary to limit visibility of parent contract's public functions?",
"description": "External/Public functions of all parent contracts will be exposed with the same visibility as long as they are not overridden.",
"remediation": "Make sure to expose only relevant functions from parent contracts.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Inheritance-2",
"question": "Were all necessary functions implemented to fulfill inheritance purpose?",
"description": "Parent contracts often assume the inheriting contracts to implement public functions to utilize the parent's functionality. Sometimes developers miss implementing them and it makes the inheritance useless.",
"remediation": "Make sure to expose relevant functions from parent contracts.",
"references": [
"https://solodit.xyz/issues/m-02-pauseunpause-functionalities-not-implemented-in-many-pausable-contracts-code4rena-stader-labs-stader-labs-git",
"https://twitter.com/bytes032/status/1736065591536935366"
],
"tags": []
},
{
"id": "SOL-Basics-Inheritance-3",
"question": "Has the contract implemented an interface?",
"description": "Interfaces are used by other protocols to interact with the protocol. Missing implementation will lead to unexpected cases.",
"remediation": "Make sure to implement all functions specified in the interface.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Inheritance-4",
"question": "Does the inheritance order matter?",
"description": "Inheriting contracts in the wrong order can lead to unexpected behavior, e.g. storage allocation.",
"remediation": "Verify the inheritance chain is ordered from 'most base-like' to 'most derived' to prevent issues like incorrect variable initialization.",
"references": [],
"tags": []
}
]
},
{
"category": "Initialization",
"description": "",
"data": [
{
"id": "SOL-Basics-Initialization-1",
"question": "Are important state variables initialized properly?",
"description": "Overlooking explicit initialization of state variables can lead to critical issues.",
"remediation": "Make sure to initialize all state variables correctly.",
"references": [
"https://solodit.xyz/issues/h-01-mintersolstartinflation-can-be-bypassed-code4rena-backd-backd-tokenomics-contest-git"
],
"tags": []
},
{
"id": "SOL-Basics-Initialization-2",
"question": "Has the contract inherited OpenZeppelin's Initializable?",
"description": "If the contract is supposed to be inherited by other contracts, `onlyInitializing` modifier MUST be used instead of `initializer`.",
"remediation": "Make sure to use the correct modifier for the initializer function.",
"references": [
"https://solodit.xyz/issues/h-03-wrong-implementation-of-eip712metatransaction-code4rena-rolla-rolla-contest-git"
],
"tags": []
},
{
"id": "SOL-Basics-Initialization-3",
"question": "Does the contract have a separate initializer function other than a constructor?",
"description": "Initializer function can be front-run right after the deployment. The impact is critical if the initializer sets the access controls.",
"remediation": "Use the factory pattern to allow only the factory to call the initializer or ensure it is not front-runnable in the deploy script.",
"references": [
"https://solodit.xyz/issues/initialization-functions-can-be-front-run-trailofbits-advanced-blockchain-pdf"
],
"tags": []
}
]
},
{
"category": "Map",
"description": "",
"data": [
{
"id": "SOL-Basics-Map-1",
"question": "Is there need to delete the existing item from a map?",
"description": "If a variable of nested structure is deleted, only the top-level fields are reset by default values (zero) and the nested level fields are not reset.",
"remediation": "Always ensure that inner fields are deleted before the outer fields of the structure.",
"references": [],
"tags": []
}
]
},
{
"category": "Math",
"description": "",
"data": [
{
"id": "SOL-Basics-Math-1",
"question": "Is the mathematical calculation accurate?",
"description": "Ensure that the logic behind any mathematical operation is correctly implemented.",
"remediation": "Verify calculations against established mathematical rules in the document or the comments.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-2",
"question": "Is there any loss of precision in time calculations?",
"description": "Loss of precision can lead to significant errors over time or frequent calculations.",
"remediation": "Use appropriate data types and ensure rounding methods are correctly applied.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-3",
"question": "Are you aware that expressions like `1 day` are cast to `uint24`, potentially causing overflows?",
"description": "Operations with certain expressions might lead to unintended data type conversions.",
"remediation": "Always be explicit with data types and avoid relying on implicit type conversions.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-4",
"question": "Is there any case where dividing is done before multiplication?",
"description": "Multiplying before division is generally better to keep the precision.",
"remediation": "To avoid loss of precision, always multiply first and then divide.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-5",
"question": "Does the rounding direction matter?",
"description": "Rounding direction often matters when the accounting relies on user's shares.",
"remediation": "Use the proper rounding direction in favor of the protocol",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-6",
"question": "Is there a possibility of division by zero?",
"description": "Division by zero will revert the transaction.",
"remediation": "Always check denominators before division.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-7",
"question": "Even in versions like `>0.8.0`, have you ensured variables won't underflow or overflow leading to reverts?",
"description": "Variables can sometimes exceed their bounds, causing reverts.",
"remediation": "Use checks to prevent variable underflows and overflows.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-8",
"question": "Are you aware that assigning a negative value to an unsigned integer causes a revert?",
"description": "Unsigned integers cannot hold negative values.",
"remediation": "Always ensure that only non-negative values are assigned to unsigned integers.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-9",
"question": "Have you properly reviewed all usages of `unchecked{}`?",
"description": "Arithmetics do not overflow inside the `unchecked{}` block.",
"remediation": "Use `unchecked{}` only when it is strictly guaranteed that no overflow/underflow happens.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-10",
"question": "In comparisons using < or >, should you instead be using \u2264 or \u2265?",
"description": "Usage of incorrect inequality can cause unexpected behavior for the edge values.",
"remediation": "Review the logic and ensure the appropriate comparison operators are used.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-11",
"question": "Have you taken into consideration mathematical operations in inline assembly?",
"description": "Inline assembly can behave differently than high-level language constructs. (division by zero, overflow/underflow do not revert!)",
"remediation": "Ensure mathematical operations in inline assembly are properly tested and verified.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Math-12",
"question": "What happens for the minimum/maximum values included in the calculation?",
"description": "If the calculation includes numerous terms, you need to confirm all edge cases where each term has the possible min/max values.",
"remediation": "Ensure the edge cases do not lead to unexpected outcome.",
"references": [],
"tags": []
}
]
},
{
"category": "Payment",
"description": "",
"data": [
{
"id": "SOL-Basics-Payment-1",
"question": "Is it possible for the receiver to revert?",
"description": "There are cases where a receiver contract can deny the transaction. For example, a malicious receiver can have a fallback to revert. If a caller tried to send funds using `transfer` or `send`, the whole transaction will revert. (Meanwhile, `call()` does not revert but returns a boolean)",
"remediation": "Make sure that the receiver can not deny the payment or add a backup handler with a try-catch.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Payment-2",
"question": "Does the function gets the payment amount as a parameter?",
"description": "For ETH deposits, `msg.value` must be checked if it is not less than the amount specified.",
"remediation": "Require `msg.value==amount`.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Payment-3",
"question": "Are there vulnerabilities related to force-feeding?",
"description": "Certain actions like self-destruct, deterministic address feeding, and coinbase transactions can be used to force-feed contracts.",
"remediation": "Ensure the contract behaves as expected when receiving unexpected funds.",
"references": [
"https://scsfg.io/hackers/unexpected-ether/"
],
"tags": []
},
{
"id": "SOL-Basics-Payment-4",
"question": "What is the minimum deposit/withdrawal amount?",
"description": "Dust deposit/withdrawal often can lead to various vulnerabilities, e.g. rounding issue in accounting or Denial-Of-Service.",
"remediation": "Add a threshold for the deposit/withdrawal amount.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Payment-5",
"question": "How is the withdrawal handled?",
"description": "The best practice in withdrawal process is to implement pull-based approach. Track the accounting and let users pull the payments instead of sending funds proactively.",
"remediation": "Implement pull-based approach in withdrawals.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-Payment-6",
"question": "Is `transfer()` or `send()` used for sending ETH?",
"description": "The transfer() and send() functions forward a fixed amount of 2300 gas. Historically, it has often been recommended to use these functions for value transfers to guard against reentrancy attacks. However, the gas cost of EVM instructions may change significantly during hard forks which may break already deployed contract systems that make fixed assumptions about gas costs. For example. EIP 1884 broke several existing smart contracts due to a cost increase of the SLOAD instruction.",
"remediation": "Use `call()` to prevent potential gas issues.",
"references": [
"https://solodit.xyz/issues/use-call-instead-of-transfer-cyfrin-none-woosh-deposit-vault-markdown",
"https://solodit.xyz/issues/m-5-call-should-be-used-instead-of-transfer-on-an-address-payable-sherlock-dodo-dodo-git",
"https://solodit.xyz/issues/m-10-addresscallvaluex-should-be-used-instead-of-payabletransfer-code4rena-debt-dao-debt-dao-contest-git"
],
"tags": []
},
{
"id": "SOL-Basics-Payment-7",
"question": "Is it possible for native ETH to be locked in the contract?",
"description": "If a `payable` function does not transfer all ETH passed in `msg.value` and the contract does not have a withdraw method, ETH will be locked in the contract",
"remediation": "Make sure either no ETH remains in the contract at the end of `payable` functions or make sure there is a `withdraw` function.",
"references": [
"https://solodit.xyz/issues/m-09-bathbuddy-locks-up-ether-it-receives-code4rena-rubicon-rubicon-contest-git",
"https://solodit.xyz/issues/m-22-eth-sent-when-calling-executeassmartwallet-function-can-be-lost-code4rena-stakehouse-protocol-lsd-network-stakehouse-contest-git"
],
"tags": []
}
]
},
{
"category": "Proxy/Upgradable",
"description": "",
"data": [
{
"id": "SOL-Basics-PU-1",
"question": "Is there a constructor in the proxied contract?",
"description": "Proxied contract can't have a constructor and it's common to move constructor logic to an external initializer function, usually called initialize",
"remediation": "Use initializer functions for initialization of proxied contracts.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-PU-2",
"question": "Is the `initializer` modifier applied to the `initialization()` function?",
"description": "Without the `initializer` modifier, there is a risk that the initialization function can be called multiple times.",
"remediation": "Always use the `initializer` modifier for initialization functions in proxied contracts and ensure they're called once during deployment.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-PU-3",
"question": "Is the upgradable version used for initialization?",
"description": "Upgradable contracts must use the upgradable versions of parent initializer functions. (e.g. Pausable vs PausableUpgradable)",
"remediation": "Use upgradable versions of parent initializer functions.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-PU-4",
"question": "Is the `authorizeUpgrade()` function properly secured in a UUPS setup?",
"description": "Inadequate security on the `authorizeUpgrade()` function can allow unauthorized upgrades.",
"remediation": "Ensure proper access controls and checks are in place for the `authorizeUpgrade()` function.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-PU-5",
"question": "Is the contract initialized?",
"description": "An uninitialized contract can be taken over by an attacker. This applies to both a proxy and its implementation contract, which may impact the proxy.",
"remediation": "To prevent the implementation contract from being used, invoke the `_disableInitializers` function in the constructor to automatically lock it when it is deployed.",
"references": [
"https://docs.openzeppelin.com/contracts/4.x/api/proxy#Initializable"
],
"tags": []
},
{
"id": "SOL-Basics-PU-6",
"question": "Are `selfdestruct` and `delegatecall` used within the implementation contracts?",
"description": "Using `selfdestruct` and `delegatecall` in implementation contracts can introduce vulnerabilities and unexpected behavior in a proxy setup.",
"remediation": "Avoid using `selfdestruct` and `delegatecall` in implementation contracts to ensure contract stability and security.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-PU-7",
"question": "Are values in immutable variables preserved between upgrades?",
"description": "Immutable variables are stored in the bytecode, not in the proxy storage. So using immutable variable is not recommended in proxy setup. If used, make sure all immutables stay consistent across implementations during upgrades.",
"remediation": "Avoid using immutable variables in upgradable contracts.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-PU-8",
"question": "Has the contract inherited the correct branch of OpenZeppelin library?",
"description": "Sometimes developers overlook and use an incorrect branch of OZ library, e.g. use Ownable instead of OwnableUpgradeable.",
"remediation": "Make sure inherit the correct branch of OZ library according to the contract's upgradeability design.",
"references": [
"https://solodit.xyz/issues/h-01-usage-of-an-incorrect-version-of-ownbale-library-can-potentially-malfunction-all-onlyowner-functions-code4rena-covalent-covalent-contest-git"
],
"tags": []
},
{
"id": "SOL-Basics-PU-9",
"question": "Could an upgrade of the contract result in storage collision?",
"description": "Storage collisions can occur when storage layouts between contract versions conflict, leading to data corruption and unpredictable behavior.",
"remediation": "Maintain a consistent storage layout between upgrades, and when using inheritance, set storage gaps to avoid potential collisions.",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-PU-10",
"question": "Are the order and types of storage variables consistent between upgrades?",
"description": "Changing the order or type of storage variables between upgrades can lead to storage collisions.",
"remediation": "Maintain a consistent order and type for storage variables across contract versions to avoid storage collisions.",
"references": [],
"tags": []
}
]
},
{
"category": "Type",
"description": "",
"data": [
{
"id": "SOL-Basics-Type-1",
"question": "Is there a forced type casting?",
"description": "Explicit type casting does not revert on overflow/underflow.",
"remediation": "Avoid a forced type casting as much as possible and ensure values are in the range of type limit.",
"references": [
"https://solodit.xyz/issues/risk-of-token-theft-due-to-unchecked-type-conversion-trailofbits-none-primitive-hyper-pdf"
],
"tags": []
},
{
"id": "SOL-Basics-Type-2",
"question": "Does the protocol use time units like `days`?",
"description": "The time units are of `uint8` type and this can lead to unintended overflow.",
"remediation": "Double check the calculations including time units and ensure there is no overflow for reasonable values.",
"references": [
"https://solodit.xyz/issues/m-05-expiration-calculation-overflows-if-call-option-duration-195-days-code4rena-cally-cally-contest-git"
],
"tags": []
}
]
},
{
"category": "Version Issues",
"description": "Vulnerabilities related to versions.",
"data": [
{
"category": "EIP Adoption Issues",
"description": "Vulnerabilities related to specific EIP.",
"data": [
{
"id": "SOL-Basics-VI-EAI-1",
"question": "EIP-4758: Does the contract use `selfdestruct()`?",
"description": "`selfdestruct` will not be available after EIP-4758. This EIP will rename the SELFDESTRUCT opcode and replace its functionality.",
"remediation": "Do not use `selfdestruct` to ensure the contract works in the future.",
"references": [
"https://eips.ethereum.org/EIPS/eip-4758",
"https://solodit.xyz/issues/m-09-selfdestruct-will-not-be-available-after-eip-4758-code4rena-escher-escher-contest-git",
"https://solodit.xyz/issues/m-03-system-will-not-work-anymore-after-eip-4758-code4rena-axelar-network-axelar-network-git"
],
"tags": []
}
]
},
{
"category": "OpenZeppelin Version Issues",
"description": "Vulnerabilities related to specific OpenZeppelin versions.",
"data": [
{
"id": "SOL-Basics-VI-OVI-1",
"question": "Does the contract use `ERC2771Context`? (version >=4.0.0 <4.9.3)",
"description": "`ERC2771Context._msgData()` reverts if `msg.data.length < 20`. The correct behavior is not specified in ERC-2771, but based on the specified behavior of `_msgSender` we assume the full `msg.data` should be returned in this case.",
"remediation": "Use the latest stable OpenZeppelin version",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-VI-OVI-2",
"question": "Does the contract use OpenZeppelin's GovernorCompatibilityBravo? (version >=4.3.0 <4.8.3)",
"description": "GovernorCompatibilityBravo may trim proposal calldata. The proposal creation entrypoint (propose) in GovernorCompatibilityBravo allows the creation of proposals with a signatures array shorter than the calldatas array. This causes the additional elements of the latter to be ignored, and if the proposal succeeds the corresponding actions would eventually execute without any calldata. The ProposalCreated event correctly represents what will eventually execute, but the proposal parameters as queried through getActions appear to respect the original intended calldata.",
"remediation": "Use the latest stable OpenZeppelin version",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-VI-OVI-3",
"question": "Does the contract use OpenZeppelin's ECDSA.recover or ECDSA.tryRecover? (version <4.7.3)",
"description": "ECDSA signature malleability. The functions ECDSA.recover and ECDSA.tryRecover are vulnerable to a kind of signature malleability due to accepting EIP-2098 compact signatures in addition to the traditional 65 byte signature format. This is only an issue for the functions that take a single bytes argument, and not the functions that take r, v, s or r, vs as separate arguments. The potentially affected contracts are those that implement signature reuse or replay protection by marking the signature itself as used rather than the signed message or a nonce included in it. A user may take a signature that has already been submitted, submit it again in a different form, and bypass this protection.",
"remediation": "Use the latest stable OpenZeppelin version",
"references": [],
"tags": []
},
{
"id": "SOL-Basics-VI-OVI-4",
"question": "Does the contract use OpenZeppelin's ERC777? (version <3.4.0-rc.0)",
"description": "Extending this contract with a custom _beforeTokenTransfer function could allow a reentrancy attack to happen. More specifically, when burning tokens, _beforeTokenTransfer is invoked before the send hook is externally called on the sender while token balances are adjusted afterwards. At the moment of the call to the sender, which can result in reentrancy, state managed by _beforeTokenTransfer may not correspond to the actual token balances or total supply.",
"remediation": "Use the latest stable OpenZeppelin version",