Say you're debugging and see that the 'foo' field of 'pointer_to_some_data' is completely bogus. You are sure that it was valid some time ago, like when its containing object was constructed, so the question is where the corruption happened. That's exactly what watchpoints are for. You set breakpoint at a code where 'foo' is known to be valid, and then ask the debugger to stop whenever the value of 'foo' changes. The debugger in turn writes the address of 'foo' to a special processor register, and processor will call back the operating system, and then debugger, when 'foo' changes.
Except that GDB does not work this way by default. If you say:
there are two interpretations. First is to stop when memory location referred to by
pointer_to_some_data->foois modified. Second is to stop when the value of the expression
pointer_to_some_data->foochanges, which can happen also if
pointer_to_some_datachanges. Obviously, when debugging memory corruption, you care about memory address, and
pointer_to_some_datais just a way to specify the memory address. Alas, by default GDB uses the second interpretation, so to set watchpoint on address you should use:
print &(pointer_to_some_data->foo) watch *$
But the problem is not just that you'll get false hits when
pointer_to_some_data changes. The thing is that if that variable is a local one, or a function parameter, then GDB will immediately remove watchpoint when you exit the containing function. So, for KDevelop user it will be like that: you pick a local variable in a variables widget, you expand it, right-click on some member, select "Toggle watchpoint", and continue. The watchpoint you've just added immediately goes away.
KDevelop 3.4 solves this problem in a radical way. All watchpoints are address watchpoints. For any expression you enter, address is computed and watchpoint is set on address. Expression without address (rvalue) can't be watched and you'll get an error message if adding watchpoints for rvalue. Additionally, when the application exits, all watchpoints are disabled, because data addresses can well be different on the next run. When user decides to enable a watchpoint, the address of expression is evaluated again, and a new watchpoints is set to that address.
Hopefully this will make watchpoints more usable for the ordinary programmer.