Yes, that's a rather nasty cut & paste error I made. But if the 31 is changed to a 15, is the code correct? I would think so. For optimization I'd think that an assembly language version would make more sense, and a few targets do that.
paul > On Dec 4, 2018, at 5:51 PM, Stefan Kanthak <stefan.kant...@nexgo.de> wrote: > > Hi @ll, > > libgcc's divmodhi4() function has an obvious bug; additionally > it shows rather poor inperformant code: two of the three conditions > tested in the first loop should clearly moved outside the loop! > > divmodsi4() shows this inperformant code too! > > regards > Stefan Kanthak > > --- divmodhi4.c --- > > unsigned short > __udivmodhi4(unsigned short num, unsigned short den, int modwanted) > { > unsigned short bit = 1; > unsigned short res = 0; > > #ifdef BUGFIX > if (den > num) > return modwanted ? num : 0; > if (den == num) > return modwanted ? 0 : 1; > while ((signed short) den >= 0) > #else // original, buggy and inperformant code > while (den < num && bit && !(den & (1L<<31))) // unsigned shorts are 16 bit! > #endif > { > den <<=1; > bit <<=1; > } > while (bit) > { > if (num >= den) > { > num -= den; > res |= bit; > } > bit >>=1; > den >>=1; > } > if (modwanted) return num; > return res; > }