So, when is code generation the right solution?
Well, not always.
If you can solve the same problem by using templates (e.g. C++) or generics (e.g. C#) then you should probably do that.
Also, if you can solve your problem with parameterization, then you might want to choose that over code generation as well. Although, that can be a matter of taste. Code generation has the advantage that it will be more efficient than a paremeterized solution, but if you aren't writing real-time applications, then you will probably not notice that little difference.
Code generation is fun. And it is easy to fall in love with it and if you do, it is easy to convince yourself that it is the solution to all problems.
So, when is code generation the right solution? Obviously, if your target language doesn't have templates or generics, then code generation will let you solve the same type of problems as you can solve with templates.
Another typical pattern is when the structure of the code you need depends on something. A good example of that is if you want to generate data access objects. They will normally have different member variables and different methods to work on the data they represent.
There are also two good examples in Visual Studio itself, web services and typed datasets. Both of those are good examples of when code generation works well. In fact, the typed dataset and the untyped dataset will help you understand what you get with a parameterized solution versus what you achieve with code generation.