There's one thing missing in this. The "virtual computer" I'll make in my head for C, Pascal and even Perl will be totaly different than the one for Lisp, Scheme, ML or Haskel and that one will again be totaly different that the one for Prolog. And SQL basicaly adds another one.
Each type of programming languages is based on a different computational model so your simulation has to be different as well. And what we need to do when programming is not to simulate what does the "actual" computer do, but what does our computation model do.
What remains is the "thinking clearly", no matter what you use you have to consider all options, you have to know your border cases, you have to know exactly what /needs to happen|will be the result|must hold true/ in any circumstance.