📖WALL OF WISDOM

In some reviews you'll do, you will find a lot of bugs and your client's fixes will be so huge, that it will require you to do a multiple of the work of the audit. Make sure you set the timeline for receiving fixes and that there is an upper limitation on how large the fix diff is. If any requirement is not fulfilled, the review requires a renegotiation. But don't be too strict about it.

Architecture is the most important thing about the codebase. If the developers thought about it enough, the codebase would be minimal. There will be few places to introduce bugs. If the contracts are large, it usually means that the architecture wasn't well done and it can pay off to look from the higher level: what is wrong with the current design?

"Use the power of comparison, whether inside of a contract, or comparing a protocol design to a similar one"
Even without understanding the purpose of a piece of code, if we know that two different implementations are supposed to do the same thing, we can check for inconsistencies. Also as SRs we see a lot of different implementations for a similar projects so that is an advantage

What you see on the surface of this space is people's success—you don't see failed attempts. Stories of successful white hats often sound like they came from nothing, but that's unrealistic. Everyone faces hardships before becoming successful.
What they have in common though is persistence! They keep going, they keep doing, and that's what actually makes them distinctly successful.

Don't forget to take a break.
What I also observe in this space is an excess of positivity. The value of your work is often equated with the time and effort you put into it.
It might sound cool to always be working on a target, spending countless nights looking for a bug. However, that's not healthy.
Don't fall into this trap and pressure. Everybody needs breaks. Remember, you'll only get the best results when you're well-rested.

Often the impact of a bug is not immediately identified. Make sure to understand the project in detail before submitting a report. With the right context, or combining the bug found with another bug, the severity level could be raised. Always double check to make sure you are not underestimating a bug's impact, and tune the PoC for maximum impact.

Sometimes you'll find a bug that is general enough that it could exist on other projects. Check all other similar projects where you could find it as well. Look through BBPs, repos, onchain contracts. While doing this, think of the possible variants of the bug as well. With some luck you could capitalize on the original bug and get some extra rewards.

"The larger the audit scope and the more complicated the protocol, the more critical your notes will be."
Note-taking is a skill that also needs to be developed to be great at auditing.
Personally, I prefer handwritten notes as my “compressed knowledge” of the codebase.
It is written as a quick reference for me. There are no huge blocks of text. It is a collection of terms, concepts, flows, and their relationships.

For me, one key aspect of finding tricky bugs is getting a very good understanding of what the code is supposed to do on a higher level by reading the documentation. Once I have that, I can start at an important part of the code and jump through the codebase following the flow of logic instead of going over a single file line by line.

The best way to continue learning is to look at all the confirmed findings I missed, after a contest.
I don't like going over old reports where I did not compete since I don't have the context of that codebase.
If I review findings from codebases I spent a lot of time on, I can more easily identify why I missed a certain issue and learn from that.

Regarding bug bounties, almost all codebases have been previously audited, often by leading security firms.
Don’t let that fool you into thinking they are bug-free. Some of my biggest bounties have been in projects that have been audited extensively and yet still were vulnerable.
Approach each codebase as if it came fresh from the developers.

Identifying a bug, writing up a PoC, and reporting it is only the first half.
The second half commonly involves quite a bit of discussion and negotiation.
Learn how to express complex technical situations, how to present a well-founded case, and how to professionally negotiate.

At which point do you stop searching a codebase for bugs?
Try to understand the system to the point where you could reimplement it from scratch without looking at the original codebase. Not from remembering the code, but from having understood what the application is supposed to do.
If you have examined a project that far and have not found a bug, the chances of finding one by continuing is low. On the other hand, if there was a bug in there, you would have most likely found it.

What sets the best researchers apart from the average ones is their ability to focus and the time they spend in a deeply concentrated state.
Human focus is like a car's fuel tank—you need to know when it needs refilling and how to use it efficiently when it's full.
Self-reflection can help you understand the conditions under which you perform at your best. Use that understanding to improve consistently and effectively.

If your goal is to uncover a high-severity bug in the X codebase and you're committed to it, your focus will naturally guide you toward success.
Approach it with the mindset of a warrior—relentless and determined—and don't give up until you're certain you've explored every possible angle to achieve your goal.

Focus on breaking the codebase rather than understanding it. Many bugs are slight logical inconsistencies that don’t even require understanding the whole picture.
Many times focusing too much on the bigger picture will yield some high-level, economical attacks but might miss out on function-specific edge cases.

The number one thing you need to succeed at hunting bugs, for bounties or contests, is having faith that you’ll find bugs.
Statistically every code base will have bugs, but that’s not how it feels when you haven’t found one in a long time.
Find out what gets you excited and hopeful, and nurture it. Consistent effort beats pretty much everything else in predicting success.

Try to learn hard things. Don’t limit yourself to the low-hanging fruit. If you learn something that most people don’t know you’ll find bugs most people miss. That can be a weird detail of the EVM or an entire field like ZK proofs. Keep pushing the boundaries of your knowledge, and collecting information on different things.

After a certain skill level pretty much anyone could find most bugs — but how do you know what targets to focus on? And for how long?
That’s the hardest part of hunting bugs, and more art than science. You might find a gold mine of bugs and report 10 in a single week, then not find any in multiple targets for months.
That’s normal. It sucks, but is normal. Try to learn with your hits and misses but don’t stress over it — it’s always unpredictable to some extent.

This changes a lot - not only about the approach to searching things, but also about what can be considered a vulnerability. For HTTP API you will need to prove that you can access admin dashboard. In web3, you need to explicitly show what you can do when you are this admin - because if worst thing you can do is start a proposal without paying fees, it will not be a high impact bug. White box gives observability, and simulation gives ability to prove things - and this means that meaning of “bug” changes from “something risky” to “something really harmful”

There is a certain moment when you should stop following the known path.
“Hacking” is about thinking differently, looking from different perspective - at least not thinking like the developer of this contract, at most thinking not like anyone else at all.
This does not mean you should not study findings of others or read new things - but you should grow your own unique approach.
Try different ideas, mix them, combine, experiment with new things. Only way to find something everyone else didn’t notice is look at it like no one else did before

Source: a point in code where an attacker supplied input enters the execution flow. Sink: a point in code where malicious state change can occur. Map the program for all Sources and trace the execution flow to determine which of them provide a path where a Sink can be reached. What safeguards are present and what would be required to bypass them? Respectively, map the program for all Sinks and retrace the steps required to reach them to identify relevant Sources. Is it possible to craft a valid transaction to reach the Sink from the Source?

Joining forces has been one of my best decisions since I started auditing. The benefits of collaboration are significant:
Enhanced Findings: Working with partners has raised the quality and quantity of our findings. We combine our ideas, transforming them into a fully developed issue. One sophisticated discovery resulted from merging two ideas:
My partner’s insight: "If we disrupt the list order, we could then employ strategy Y to potentially cause users to lose funds."
My idea: "Implementing strategy X might let us break the list order."

Understanding the application logic and being able to read a bit of the specific programming language is sufficient for finding bugs;
Expertise in that language is not mandatory.
You don’t need to stick exclusively to Solidity to hunt for bugs.
Although I lack expertise outside of Solidity, I've successfully reported bugs in Vyper, Rust, Cairo, Move, and other languages.

When evaluating the impact of a bug, keep the Dilution Effect in mind.
Suppose you identify two possible impacts of an exploit: one with high impact and the other with low.
As a bounty hunter, you may feel inclined to mention both, but this can backfire.
The weaker impact can dilute the stronger one, as people tend to average the effects rather than summing them up. You're better off emphasizing the higher impact alone. Source: The Counterintuitive Way to Be More Persuasive by Niro Sivanathan (TED Talk)

When auditing an unfamiliar codebase, it's essential to thoroughly review related third-party codebases first. For instance, when auditing a new chain based on Cosmos SDK and Geth, you should:
Study key APIs like Cosmos SDK's PrepareProposal/ProcessProposal/FinalizeBlock/ExtendVote/VerifyVoteExtension functions.
Understand Geth's block generation/verification/processing steps.
Research known vulnerabilities discovered by other security experts.
This approach helps you understand both the complete code flow and potential security risks, providing valuable insights for your audit

Thoroughly review the attack path firstly.
Take a break, then review it again with fresh eyes.
If the vulnerability still holds after double review, develop a Proof of Concept (PoC).
Remember that ideas often rely on assumptions that may be incorrect, especially in complex codebases. Following this systematic approach helps build experience and reduces errors in future audits.

This has worked like a charm to me.
The idea here is to be able to think how everything should behave prior to actually diving in the implementation. This will allow you to identify things missing in the protocol, or to check unexpected behaviors that might lead to bugs.

Currently, there are far more opportunities in Web3 security than anyone could have imagined even a year ago.
Pick one niche and excel at it, capitalize on it as much as possible. Then, you can expand your knowledge afterward. Don't try to chase and master everything early in your journey

It's one of the worst things that can happen. It can occur especially in very large codebases.
Once it made us lose the only spotted High vulnerability in a public C4 contest which awarded the solo spotter a 6 figure prize.
I had the risk in my notes, I highlighted the code snippet with the audit tag before, and failed to validate it as I lost the code logic at the end of the contest.

While this could be subjective - as many people suggest that it leverages Game Theory by not doing so - I observe that I don't see any flaws in the codebases that I disliked.
This often leads to simply passing time without purpose and can deepen feelings of imposter syndrome once those flaws become apparent.

A mitigation can fix a bug, partially fix a bug, not fix a bug or expose another vulnerability in the code. It can also do a combination of these. You can always check if a mitigation does any of these.
I've seen a mitigation to a problem I reported partially fix a problem and allow me still exploit the vulnerability.

Once you understand the structure and flow of a system, narrow your focus to a single variable. Identify all the changes it undergoes and assess whether these changes are intended. Tools like "Ctrl+F" are key for tracking variables efficiently. I’ve seen 0xSimao mention this strategy on X.

The vast majority of vulnerabilities are due to logical flaws or a lack of constraints and don't require a deep understanding of the EVM's inner workings. These are found by training your auditing skill through deliberate practice.
So in terms of technical knowledge, you can achieve great results if you just learn the basics thoroughly (e.g as much as @CyfrinUpdraft teaches).

It’s better to do less work on 100% than double the work on 50%. My belief is that if you do a 100% job, you get 100% result.
But if you do a 50% job, you get 25% result. You work with code every day, you use your brain to uncover sophisticated attacks. You need 100% focus. You need good sleep, good diet and a lot of energy. Take a break sometimes, work out / walk daily, go on a hike

This applies especially to audit contests. You work your ass off on an audit just to find out that you made a few cents in the end. That is the best thing that can happen to you!
First you can learn from the findings you did not find and make sure that you will never miss those again.
Second you can retrospect on your process and see what should be improved, maybe based on the reasons why you missed some findings.
Third this should make you want to compete more and more fiercely with the new knowledge to beat everyone the next time.
My biggest achievements started when I changed my approach after I realised I have not reported vulnerabilities worth ~$40k that I saw during the competitions:)

There is some good in financial success that might be a good driver forward, that’s why you should hunt in blue oceans - focus where the least focus is to maximise your profit.
Why compete with thousands when you can compete with tens?:) Compete does not necessarily means audit competitions, businesses are competing for customers etc.

This means that audit to me signals some guy in suit checking if something is correct. You are not a unit test, you should not check if it is working correctly.
You should check how to exploit it for your financial gain! Or how to exploit it to hurt the users, or the protocol itself. You are the attacker!
Of course, you are the good guy, so once you uncover the bug, you responsibly report it:)

I changed my process several times, in the beginning after almost every audit, until I found what suits me the best.
Key insights from my process is analyse what you are doing (drawings, use case diagrams, flow charts, state machine), identify attack vectors and create threat models, and then just break the code.

A wise person once said: work, work, work, work, work, work
It was Rihanna.
"Idk man, you just need to put in the work" is like the most generic thing you could tell someone who wants advice on how to get gud (at anything), but sadly the answer is as true as it is unsexy.
I like to consider myself fairly smart. I had an easy time in school and university, I could half-ass most of it and still get very good grades. I had to learn the hard way that this mentality does not transfer to the security research space.
This place is filled with giga-brains, and the only option for most people to get anywhere close in terms of skill is to outwork them.

I am a massive sucker for FOMO. I can not count the times where I tried to do contests in parallel or when I was planning to do a contest in the final third of the time available just so I could do another one before that, for which I also only allocated a fraction of the time I should have. Needless to say I did not perform well doing this, ever. Remember how I said earlier that I consider myself smart? It's moments like these that make me question if I don't have a learning disability instead (like in the Simpsons episode where Lisa tests if her brother is dumber than a hamster) Learn from my mistakes and dedicate yourself to one codebase at a time for as much time as necessary until you understand how everything works.

This is a funny meme, but it's just that.
If you are you are far enough to the right of the intelligence curve you may be able to get away with it, but for most people I don't believe its an efficient way to go. Obviously reading code is the majority of the job, but for those who are not blessed with extraordinay mental RAM, there is no shame in:
reading the docs to get a high-level understanding first
taking notes and drawing diagrams
using an IDE and learning to use it properly
(especially in regards to navigating and searching code)

Previous findings can present valuable opportunities. Always review past audits and analyze the fixes; often, less time is spent auditing these corrections.
Remember that fixes can create new problems or may not be implemented correctly, leading to potential vulnerabilities.

Allocate as much time as possible to review the complex logic (math, multi-contracts interactions, novel design, etc). You need creativity, knowledge and a good mental model to find the most complex bugs. These are the ones that are not obvious and typically involves multiple step or specific edge case to exploit. With the saved time from the initial phase, you increase your odds of spotting the more complicated issues.

Take notes about everything, from how a tricky function works, to all the attack vectors I’ve already thought about while exploring the contracts.
Write all the doubts and ideas of potential attack vectors/bugs and always return to them once you’ve understood every detail of the codebase.
Save all the articles (EIPs, deep downs of X protocol) you consulted for future reference.

While auditing, focus your attention on exploring paths that would allow an attacker to steal assets from the contracts. More often than not you’ll get false positives/dead-ends, but, in the process of exploring these paths you’ll end up understanding the codebase from top to bottom and the non-critical bugs will pop up right in front of you.

If you make a great achievement like winning a contest or a bug bounty, you should seize this hype and make the most benefits from it, such as joining invitational audits or marketing to yourself to get more opportunities such as private audits and build your experience. Do not stop or take a rest after making good results.

When deciding on what contest to look at, nowadays its becoming more and more important to know if a contest will contain highs, due to scaled pots. You can usually predict the chances of this pretty well by looking at 3 metrics:
Prior audits -> Who audited it before? In case of no one or a low quality company we can be pretty sure to find stuff
Code quality -> If there is almost no testcases or documentation, we can usually expect highs
Size -> The bigger the codebase is the better as the chance of highs increases exponentially

So if I do a scaled pot, in the best case I want those 3 to align.
A big codebase, that is badly documented / tested and had no or only low quality audits before. In that case you can be almost sure that the pot is unlocked, but competition will still be a lot lower due to the pot being scaled.

I always try to meet as many people in the industry as possible.
First of all you will find a lot of friends that have a similar mindset to you which is awesome.
Second of all these friends can be helpful all along the way. I have gotten many opportunities or clients referred to me by friends I met along the way.

"Don't be a leech 🐛"
If you just want others to help you but not do anything for them no one will want to be your friend. Try to help and support each of your friends whenever you can. It might be referring a client to them, it might be putting a good word in for them with someone you know etc. This way you can build lasting friendships out of which both sides profit.

If you're just starting out and planning to participate in your first contest, make sure to properly equip yourself before stepping into the battlefield. One of the main reasons many newcomers give up early is that they jump straight into a contest without preparation. Often, they struggle to find anything, feel overwhelmed, and conclude that success is impossible- leading them to quit. On the other hand, auditors who spend a few weeks preparing by conducting shadow audits, reading reports, and actively practicing finding bugs, tend to perform reasonably well in their first contest. This initial success is what you need to ignite the motivation needed to persevere and continue until you truly "make it."

This is where unique and less duplicated findings hide. If you stay on the surface, where everyone else is, you'll uncover the same issues as everyone else. But if you're bold enough to dive deeper, you can win Big. The deeper you go, the less competition you'll face. Going deep means that once you understand how a protocol works, you focus on its most critical flows, break them down into smaller components, and start exploring:
are there any external integrations -> study the external integration code
check tests for a particular flow -> are there any spots left untested -> explore them
are there any exotic scenarios to this flow -> try to think of them and see if they brake the logic

Remaining focused is one of the most essential principles to grasp in this industry, and it applies on multiple levels:
Commit to one contest at a time and give it your all - It's far better to win a single contest than to perform moderately well in several.
Dedicate yourself to one goal - Whether it's becoming an LSR/LSW, building a business, or excelling at bug bounties, choose a single goal and channel all your efforts into achieving meaningful results.

Once you’ve built some initial recognition (achieving a few milestones helps break the ice quickly), start connecting with other auditors.
Share your opinions, expectations, and experiences with them—this can help you identify false assumptions and recalibrate your approach to make more informed and effective decisions
This is one of the best ways to stay updated on real trends and opportunities in the industry—those that lie behind the glossy marketing facade.

Always welcome the opportunity to dive one step deeper, to understand the code at an even lower level, to develop an even more precise understanding of the whole stack.
But do it with a purpose - also accept that it is simply infeasible to learn and retain all there is to know about any single blockchain. So pick your battles, and fight.

Good auditing skills come from auditing. You need some reference material to get started, but after that, learning by doing is how you improve.
Contest platforms provide a feedback loop, community, scheduling, the right incentives and most importantly, a payout. Make use of the structures available to you.

When your goals are set too low, it's so easy to quit or lose interest after some success.
Your goals should be so high that reaching them will truly change your life. There are so many memes about BJJ people leaving training after getting their blue belt, but when your goal is to be the most badass grappler in the world, no belt will make you quit the game.

As I strongly believe that we’re put here to give more to this earth than to receive, hoping to get everything we’re dreaming of without giving back at least equally, it won’t happen. If your dreams are high, you need to be ready to pay more.
And the right way to be able to give more is by working on YOU every day, being a greater version of YOU!

When someone's performance seems unreachable, it doesn't mean it is. All you need to reach that level is consistency. You'll level up without even realizing how much you've grown with just consistent work. For example, when I started jiu-jitsu, blue belts seemed so powerful and untouchable. I felt unprotected and thought I'd never reach their level. But now, I can play with newcomers and submit them easily. All it took was 8-9 months of consistent training

A bit controversial, but also include informational and low issues when possible. The act of putting into writing a potential low issue both solidifies your understanding of the codebase and provides a slight benefit for the protocol. Countless times, while thinking about how to report an informational issue on a part of the code, I realized there were more issues there.

"The Hunter Should Not Be Jealous of the Builder's Hammer, and the Builder Should Not Envy the Hunter's Bow"
What works when hunting on bug bounties may not be as relevant when doing private engagements or contests.
Although similar, different applications of auditing require different approaches. Remember this and do not try to apply a bug bounty hunter mindset to a private engagement, or vice-versa.

Your resource is your brain, but it has its quirks. You may focus for hours on a codebase only to find an issue later while showering. Why? Because you entered a diffuse thinking mode.
Relax your thinking intentionally to allow the pieces to fall into place and the issue to reveal itself to you. Plan walks, long baths, or other such activities in between focus sessions.
Last updated