??? 06/08/11 15:09 Read: times Msg Score: +3 +3 Good Answer/Helpful |
#182541 - Stop wondering about the compiler output Responding to: ???'s previous message |
Sandy B. Pal said:
Here I'm inserting part[1] of the code. The same is copied in part[2] & part[3] with only changes with respect to month & year limits. Your text indicates that you still are convinced that the compiler should do exactly the same thing in assembler just because you see the same thing in C. It's enough that the compiler notices that the jump distance is different long, for the compiler to consider different conditional testing + jump code in the assembly output. Not only that - the compiler does not build code 1-to-1. It converts your C code into a data structure. A form of tree with operators and operands like you have for evaluating a normal equation but quite a bit bigger. It (it or in some situations even the linker) then performs a number of optimization passes on this intermediate representation, before real assembler instructions are generated. Some compiler packages - like Keil - performs some of the optimization steps all the way down in the linker, since it's only the linker that can know the actual position of the different variables and functions. How they overlap or how far away they are. But performing such optimization steps on an intermediate representation also means that tree actions before or after your specific code lines can merge with each other, changing places. So the optimization logic can see a different opportunity to optimize the first "identical" block than the middle blocks or the last block. In the end, you use C if you want to solve a problem. And you write your own assembler if you want/need to solve that problem using specific instructions. Listing files are good to have. But the normal reasons for being able to see the assembly output are: - making it possible to compare a good and bad compiler - making it possible to get an idea what gain/losses you get from different optimizations. - making it possible to detect C constructs the compiler have a hard time with, and that can be compiled in a better way if the C code is rewritten. - (for some compiler) getting a template for how to call a C function from assembler, or how to write an assembler function that can receive parameters and send back answers and from the outside looks lika a normal C function. - figuring out strange problems with code. If they are caused by a compiler bug, or (more probably) by an invalid assumption (such as alias, volatile, evaluation order...) by the C programmer. Your reason for looking at the assembly output is totally flawed, since you have decided that you should be able to look at C code and predict what the compiler should emit. Such prediction is only possible when having a machine translation between two languages that have a perfect 1-to-1 relation. The C to assembler conversion allows much too many alternatives, and there are much too many potential optimization steps when performing strength reduction, peephole optimization, evaluation reordering, ... If you want 100% control: go assembler. Just don't make the mistake that 100% control means better code, or faster code, or saves you money. The intention with high-level (even if C isn't so very high-level) languages is to make you better see the code constructs, while reducing the potential execution paths. So a good assembler programmer can win over the compiler. But lots of assembler programmers will not be able to get close, without having to write total spaghetti code. After all, the compiler is allowed to produce spaghetti code since the output is not designed (and should not have to be designed) for readability. The original language is the one designed for readability, while the compiler may use whatever trick it knows to run fast or take little space. In the end, you can spend weeks, months or years looking at output from a compiler and not be able to figure out exactly why it made a specific conversion. The total set of rewrite rules used by the compiler is too vast, so even the compiler developer would need to look at trace output to find out the exact rules evaluated by the compiler, and what weight the rules got, and which priorities that was then used. |
Topic | Author | Date |
Compiler variations?? | 01/01/70 00:00 | |
Fundamental philosophy of High-Level Languges (HLL) | 01/01/70 00:00 | |
C code | 01/01/70 00:00 | |
and so what | 01/01/70 00:00 | |
Stop wondering about the compiler output | 01/01/70 00:00 | |
Very nice to learn this important matter | 01/01/70 00:00 | |
Exactly what you wrote | 01/01/70 00:00 | |
volatile sbit may be the problem | 01/01/70 00:00 | |
read up on (not) volatile | 01/01/70 00:00 | |
Look at my profile | 01/01/70 00:00 | |
Not offence intended | 01/01/70 00:00 | |
defining P0_6 so that compiler doesn't treat it as volatile | 01/01/70 00:00 | |
Skip the goto - almost always exists beautiful rewrites | 01/01/70 00:00 | |
Goto really is a bastard code construct | 01/01/70 00:00 | |
and therefore ... | 01/01/70 00:00 | |
Will come back with modified code | 01/01/70 00:00 | |
Wonderful as always! | 01/01/70 00:00 |