Thursday, August 12, 2010

OK, I'm officially done with DIV stuff, but I've learned a few things while working on this. I tried everything I could think of to try to get the register location to work properly on argument 1 and the outputs. No luck. Every attempt using subregs, or direct register assignment resulted in working code, but seperate blocks for DIV and MOD. Apparently, the optimizer is not smart enough to deal with this properly. If any modification is done to argument 1, the blocks get split again. Also, I can't find a way to specify one argument as a subreg of another argument.

So, in order to make the best of this situation, I'm using a form which does not tie output registers to argument one. This allows the optimizer to group DIV and MOD operations with common terms. On the other hand, this allows the outputs to be located in inconvenient registers. Code has been added to move the results to the registers selected by the compiler. In the worst case, the DIV and MOD results are in the opposite registers (MOD result rgister chosen to hold DIV, and vice versa). This case is handled by swapping values using XOR, which eliminates the need for a temp register, but is no faster than just using MOVs. In a perfect world, this work would be unnecessary, but this is better than having seperate DIV and MOD blocks. With careful ordering in the C code, the compiler can be encouraged to use the correct registers, omitting all the extra MOVs.

So now, unless something else pops up, I can put the compiler to rest, and continue with the LIBC code.

No comments:

Post a Comment