summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authormar77i <mar77i@protonmail.ch>2017-08-07 15:51:01 +0200
committermar77i <mar77i@protonmail.ch>2017-08-07 15:53:18 +0200
commit5865c1396c7ccd8a18d5147ef238e86c75dee93e (patch)
tree469ca9b70c30ba825c8e8689e040de7327ccd1f3
parent1d2441778ae51a1aaf567358a5a30740ee39de98 (diff)
use an easier to understand base32 decoder
-rw-r--r--otp.c57
1 files changed, 41 insertions, 16 deletions
diff --git a/otp.c b/otp.c
index de06a61..1584d30 100644
--- a/otp.c
+++ b/otp.c
@@ -41,31 +41,56 @@ int concat(char *dest, size_t *dest_used, size_t dest_size, char *src) {
int b32_decode(unsigned char *buf, size_t *len) {
const char alphabet[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ234567";
- size_t i = 0;
- char x = 0, *ptr;
- unsigned char *output = buf, count, lsh;
- if(buf == NULL)
- return -1;
- for(count = 1;; count++) {
- while(isspace(buf[i]))
+ size_t i = 0, used = 0;
+ unsigned char x, *output = buf;
+ char *ptr;
+ for(;;) {
+ while(isspace(buf[i]) || buf[i] == '\n')
i++;
- if(buf[i] == '\0')
+ if(buf[i] == '\0' || buf[i] == '=')
break;
ptr = strchr(alphabet, toupper(buf[i++]));
if(ptr == NULL || *ptr == '\0')
return -1;
x = ptr - alphabet;
- if(x < 0)
- return -1;
- lsh = (count * 3) % 8;
- if(lsh > 3)
- *output |= x >> (8 - lsh);
- if(lsh + (count > 1) > 3)
+ switch(used++ % 8) {
+ case 0:
+ *output = x << 3;
+ break;
+ case 1:
+ *output |= x >> 2;
+ output++;
+ *output = x << 6;
+ break;
+ case 2:
+ *output |= x << 1;
+ break;
+ case 3:
+ *output |= x >> 4;
+ output++;
+ *output = x << 4;
+ break;
+ case 4:
+ *output |= x >> 1;
+ output++;
+ *output = x << 7;
+ break;
+ case 5:
+ *output |= x << 2;
+ break;
+ case 6:
+ *output |= x >> 3;
output++;
- *output = (x << lsh) | ((lsh < 3) * *output);
+ *output = x << 5;
+ break;
+ case 7:
+ *output |= x;
+ output++;
+ break;
+ }
}
if(len != NULL)
- *len = output - buf + 1;
+ *len = output - buf;
return 0;
}