もしエラーがプログラムを異常終了させるほど深刻なものだったなら、バグの存在は明らかである。プログラムがそこまで深刻ではない問題を検出した場合、エラーとなるかログメッセージが表示されるかすると、バグの存在を認識できる。しかしエラーが軽微で間違った結果を出すだけであったら、バグの存在を検出するのははるかに難しくなる。これはプログラムの結果を検証するのが困難であるか不可能である場合に特に成り立つ。
このステップの目的はバグのしるしを特定することである。問題のしるし、どのような条件の下で問題が起き、（可能なら）どのような回避策があったか、を観測することは後のステップで問題点をデバッグする大きな助けとなる。
バグの発生源を分離する.
このステップはシステムのどの部分が問題を引き起こしているかを特定するものである。これは度々デバッグ作業で最も困難な（ゆえにやりがいのある）ステップとなる。都合の悪いことに問題の発生箇所は兆候の出現箇所と常に同じであるわけではない。例えば、入力レコードが破壊されていたら、プログラムが別のレコードを処理したり間違った情報に基づいて動作するまでエラーは起きないことがあり、その場合レコードが読み込まれてから長い時間が経ってしまっている。
このステップは反復的なテストを必要とすることが多い。プログラマは最初に入力が正しいことを検証し、次に正しく読み込まれたか、正しく処理されたかなどを検証していく。モジュール化されたシステムではモジュール間のインタフェースを通してやり取りされるデータの妥当性を検査することで、このステップをわずかに楽にすることができる。入力が正しく、しかし出力がそうでなければ、エラーの発生源はそのモジュールの中にある。入力と出力を反復的にテストすることでデバッガはエラーが起きている箇所を数行のコードまで特定することができる。
バグの原因を特定する.
バグの位置を見つけたら、次のステップはバグの実際の理由を突き止めることである。これにはプログラムの他の部分を調べることが必要な場合がある。例えば、データのフィールドが間違っていたためにプログラムが停止したとする。この次のステップはフィールドが間違っていた理由を特定することであり、それがバグの真の発生源である。プログラムが不正なデータに対処できないこともバグとみなせると主張する者もいるが。