summaryrefslogtreecommitdiff
path: root/user
diff options
context:
space:
mode:
authorAditya Naik2021-01-31 06:05:55 -0500
committerAditya Naik2021-01-31 06:05:55 -0500
commit951e300c10613c8500705d7b54467169be53a7f5 (patch)
tree0ea92fc4b6f75e6c6bb96e37bf26ffe371135f08 /user
parent077323a8f0b3440fcc3d082096a2d83fe5461d70 (diff)
With only RISCV64-I extension
Diffstat (limited to 'user')
-rw-r--r--user/printf.c35
1 files changed, 33 insertions, 2 deletions
diff --git a/user/printf.c b/user/printf.c
index 5c5c782..2b9cd06 100644
--- a/user/printf.c
+++ b/user/printf.c
@@ -12,6 +12,36 @@ putc(int fd, char c)
write(fd, &c, 1);
}
+int mul(int x, int y)
+{
+ int ret = x;
+ for (int tmp = y-1; tmp > 0; tmp--) {
+ // Add higher and lower 16 bits seperately
+ // apparently gcc uses muldi3 builtin while adding long long ints
+ int rettmp = ret;
+ ret = (((uint16)(x>>16))+((uint16)(rettmp>>16)));
+ ret += (((uint16)(x&0xffff))+((uint16)(rettmp&0xffff)));
+ }
+ return ret;
+}
+
+int mod(int x, int y)
+{
+ int idx = 0;
+ for (idx = 0; mul(idx, y) <= x; idx++);
+ idx = x-mul((idx-1), y);
+ return idx;
+}
+
+int div(int x, int y)
+{
+ if (y >= x)
+ return 0;
+ int ret = 1;
+ for (; (x=x-y) >= y; ret++);
+ return ret;
+}
+
static void
printint(int fd, int xx, int base, int sgn)
{
@@ -29,8 +59,9 @@ printint(int fd, int xx, int base, int sgn)
i = 0;
do{
- buf[i++] = digits[x % base];
- }while((x /= base) != 0);
+ buf[i++] = digits[mod(x, base)];
+ x = div(x, base);
+ }while(x != 0);
if(neg)
buf[i++] = '-';