static int ppunum(unsigned int n, int base) { unsigned int m; int nchars; #if 1 char *chars = "0123456789abcdef"; #else char chars[16]; chars[0]='0';chars[1]='1';chars[2]='2';chars[3]='3';chars[4]='4'; chars[5]='5';chars[6]='6';chars[7]='7';chars[8]='8';chars[9]='9'; chars[10]='a';chars[11]='b';chars[12]='c';chars[13]='d';chars[14]='e'; chars[15]='f'; #endif { int z; if( n == 0 ) return 0; #if 0 obyte('X'); obyte(1); oword(0x12345678); obyte(0); z = __multiply(3,5); obyte(1); oword(z); obyte(0); obyte(1); oword(0x88664422); obyte(0); z = __divide(32,16); oword(z); obyte(1); oword(0x11335577); obyte(0); #endif m = n/base; } nchars = ppunum(m,base); obyte(chars[n%base]); return nchars+1; }
static void do_fact(int n) { unsigned long long res = 1; u_int8_t *res_str = NULL; u_int8_t *i_str = NULL; int i, len_res = 0, i_str_len = 1, last_str_len = 0, cur_radix = 10; size_t offset_res = 0; for(i = 2; i <= n; ++i) { if(!(i % cur_radix)) { cur_radix *= 10; last_str_len = i_str_len; ++i_str_len; } if(!res_str) { res = __multiply(res, i, &res_str, &len_res, &offset_res); } else { if(last_str_len != i_str_len) { last_str_len = i_str_len; i_str = realloc(i_str, i_str_len + 1); } snprintf((char*)i_str, i_str_len+1, "%d", i); /*printf("Computing fact [%d] * [%d] -- [%s * %s]\n", i-1, i, res_str + offset_res, i_str);*/ res_str = __slow_multiply(res_str + offset_res, i_str, i_str_len, &len_res, &offset_res); } } if(res_str) { printf("%s\n", *(res_str + offset_res) == '0' ? res_str+offset_res+1 : res_str+offset_res); } else printf("%llu\n", res); if(i_str) free(i_str); }