Semantics, in my book, does cover abstraction. There is a trick I use while designing. If I cannot come up with a clear, simple name for a class or method, I probably have a bad design. Confusing names are a sign of a confusing design.Interesting thoughts from Bob. [Hard Werken], quoted in [rebelutionary]
One very useful XP practice (and one of the more difficult) is the adoption of a system metaphor. You model the system you are building on something that is similar in function that already exists. The metaphor helps a great deal with naming things, because you can relate the thing you are building back to the metaphor.
One project we worked on involved receiving data from a number of clients wrapped in some crypto (we had to write the client, too), passing the data on to a third party, and billing the sender. Early in the design stage, we caught on to the idea of having a courier service as our metaphor. Immediately, we had a naming scheme - the crypto became the envelope, the checksum was its seal, the envelope was "weighed" to determine its cost, and then passed to the dispatcher.
Also, the metaphor helped a lot with scoping the project. Once you understand a project in terms of something real and simple to understand (like a courier), you could realise that some features that were on the list would never be used (because nobody would ask their courier to do that), or that some things that weren't on the list were vital.
Of course, coming up with the metaphor in the first place can be really, really tough.