As assembly instruction sets are reasonably complex, properly figuring out a function boundaries inside a big executable binaries is a somewhat difficult task. Even IDA, which specializes in that, has quite a few mistakes and misses in certain scenarios.
This goes back to disassembly strategies, which are basically the algorithm used to provide disassembly listings for given stream of binary. They're often divided to two categories:
- Linear Sweep is to simply disassembly one instruction after the other. The straight-forward way to disassemble a sequence of instructions - start the next instruction disassemble right where the last instruction ended.
- Recursive Disassembly attempts to consider the code flow while disassembling, and will likely hold a stack of "function entries" (every call, for example, will get it's target address in that queue). The queue keeps being emptied by the disassembly engine until all encountered functions are analyzed.
They both have their pros and cons although Linear sweep is considered simpler to implement and recursive disassembly to yield better results.
Most debuggers don't focus too much on the disassembly task because usually, instruction pointer registers will point to the correct function to disassemble and the need to disassemble big binary blobs and recognise functions is rare. Additionally, as mostly static analysis tool IDA puts a lot more focus into exposure of the "whole picture", where debuggers tend to shine a light on only a small piece of the executable at a time.
x64dbg is another debugger (considered an ollydbg replacement by some) with decent function discovery.