From c9e045dc2170a99c9f32386e3e53aee9e01a8e7c Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Mon, 30 Dec 2019 17:34:23 +0100 Subject: io api rework --- strings.c | 73 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 73 insertions(+) create mode 100644 strings.c (limited to 'strings.c') diff --git a/strings.c b/strings.c new file mode 100644 index 0000000..55aff97 --- /dev/null +++ b/strings.c @@ -0,0 +1,73 @@ +#include + +#include "strings.h" + +void uint32_to_dec(uint32_t number, char buf[10]) +{ + for (int i = 0; i < 10; i++) + { + buf[10 - 1 - i] = number % 10; + number /= 10; + } +} + +void uint32_to_hex(uint32_t number, char buf[8]) +{ + for (int i = 0; i < 8; i++) + { + unsigned char quadbit = (number >> ((8 - i - 1) * 4)) & 0xf; + buf[i] = quadbit > 9 ? quadbit - 10 + 'a' : quadbit + '0'; + } +} + +void uint32_to_bin(uint32_t number, char buf[32]) +{ + for (int i = 0; i < 32; i++) + buf[i] = ((number >> (32 - i - 1)) & 1) ? '1' : '0'; +} + +void uint32_to_decstring(uint32_t number, char buf[11]) +{ + uint32_to_dec(number, buf); + buf[10] = '\0'; +} + +void uint32_to_hexstring(uint32_t number, char buf[9]) +{ + uint32_to_hex(number, buf); + buf[9] = '\0'; +} + +void uint32_to_binstring(uint32_t number, char buf[33]) +{ + uint32_to_bin(number, buf); + buf[32] = '\0'; +} + +void trim_0s(char string[]) +{ + size_t i; + for (i = 0; string[i] != '\0' && string[i] != '0'; i++); + + size_t j = 0; + + if (string[i] == '\0') + string[j++] = string[i--]; + + do + string[j] = string[i + j]; + while (string[j++]); +} + +void uint32_to_decstringt(uint32_t number, char buf[11]) +{ + uint32_to_decstring(number, buf); + trim_0s(buf); +} + +void uint32_to_hexstringt(uint32_t number, char buf[9]) +{ + uint32_to_hexstring(number, buf); + trim_0s(buf); +} + -- cgit v1.2.3 From 142439f7240bf796dba4ed4e570c6df0a33997b1 Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Mon, 30 Dec 2019 20:16:44 +0100 Subject: uint32_to_hexstring() bugfix --- strings.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'strings.c') diff --git a/strings.c b/strings.c index 55aff97..34c269a 100644 --- a/strings.c +++ b/strings.c @@ -35,7 +35,7 @@ void uint32_to_decstring(uint32_t number, char buf[11]) void uint32_to_hexstring(uint32_t number, char buf[9]) { uint32_to_hex(number, buf); - buf[9] = '\0'; + buf[8] = '\0'; } void uint32_to_binstring(uint32_t number, char buf[33]) -- cgit v1.2.3 From a2885ace9af6b78172837734ddd3a0ea269e1734 Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Mon, 30 Dec 2019 23:40:08 +0100 Subject: fix number trimming --- strings.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) (limited to 'strings.c') diff --git a/strings.c b/strings.c index 34c269a..fb3b0ac 100644 --- a/strings.c +++ b/strings.c @@ -47,12 +47,12 @@ void uint32_to_binstring(uint32_t number, char buf[33]) void trim_0s(char string[]) { size_t i; - for (i = 0; string[i] != '\0' && string[i] != '0'; i++); - + for (i = 0; string[i] == '0'; i++); + size_t j = 0; - if (string[i] == '\0') - string[j++] = string[i--]; + if (!string[i]) + string[j++] = string[--i]; do string[j] = string[i + j]; -- cgit v1.2.3 From 47cebef7a2e4dd66be9f7f6b0b8e8cadfeb6064a Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Tue, 31 Dec 2019 10:32:47 +0100 Subject: add strlen implementation --- strings.c | 8 ++++++++ strings.h | 2 ++ 2 files changed, 10 insertions(+) (limited to 'strings.c') diff --git a/strings.c b/strings.c index fb3b0ac..7c87e29 100644 --- a/strings.c +++ b/strings.c @@ -71,3 +71,11 @@ void uint32_to_hexstringt(uint32_t number, char buf[9]) trim_0s(buf); } +size_t strlen(char string[]) +{ + size_t len; + + for (len = 0; string[len]; len++); + + return len; +} diff --git a/strings.h b/strings.h index bfe6fd0..7e772d3 100644 --- a/strings.h +++ b/strings.h @@ -21,4 +21,6 @@ void uint32_to_decstringt(uint32_t number, char buf[11]); void uint32_to_hexstringt(uint32_t number, char buf[9]); +size_t strlen(char string[]); + #endif // STRINGS_H -- cgit v1.2.3 From 1126a18822701632e5914e441386c7fa5d2cf474 Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Tue, 31 Dec 2019 10:35:00 +0100 Subject: fix number to decimal string conversion --- strings.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'strings.c') diff --git a/strings.c b/strings.c index 7c87e29..4164467 100644 --- a/strings.c +++ b/strings.c @@ -6,7 +6,7 @@ void uint32_to_dec(uint32_t number, char buf[10]) { for (int i = 0; i < 10; i++) { - buf[10 - 1 - i] = number % 10; + buf[10 - 1 - i] = '0' + (number % 10); number /= 10; } } -- cgit v1.2.3 From 8025e6b92a09fcf584c13fea3f04f2a0be9cbe64 Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Tue, 31 Dec 2019 11:05:33 +0100 Subject: add memcpy --- strings.c | 16 ++++++++++++++-- strings.h | 3 +++ 2 files changed, 17 insertions(+), 2 deletions(-) (limited to 'strings.c') diff --git a/strings.c b/strings.c index 4164467..94cb6ac 100644 --- a/strings.c +++ b/strings.c @@ -1,5 +1,3 @@ -#include - #include "strings.h" void uint32_to_dec(uint32_t number, char buf[10]) @@ -79,3 +77,17 @@ size_t strlen(char string[]) return len; } + +void memcpy(void *dst, void *src, size_t nbytes) +{ + size_t iter; + + // copying by word is faster than by byte + // copy by word as much as possible + for (iter = 0; iter < nbytes / 4; iter++) + ((volatile uint32_t*) dst)[iter] = ((uint32_t*) src)[iter]; + + // copy the remaining 1, 2 or 3 bytes by byte + for (iter *= 4; iter < nbytes; iter++) + ((volatile uint8_t*) dst)[iter] = ((uint8_t*) src)[iter]; +} diff --git a/strings.h b/strings.h index 7e772d3..1eb291c 100644 --- a/strings.h +++ b/strings.h @@ -1,6 +1,7 @@ #ifndef STRINGS_H #define STRINGS_H +#include #include void uint32_to_dec(uint32_t number, char buf[10]); @@ -23,4 +24,6 @@ void uint32_to_hexstringt(uint32_t number, char buf[9]); size_t strlen(char string[]); +void memcpy(void *dst, void *src, size_t nbytes); + #endif // STRINGS_H -- cgit v1.2.3 From fa42eccf0b9c6161be0ad9e3c1b7f6489add2b2c Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Tue, 31 Dec 2019 11:09:57 +0100 Subject: move memset() implementation to strings.c --- demo_functionality.c | 11 ----------- strings.c | 15 +++++++++++++++ strings.h | 2 ++ 3 files changed, 17 insertions(+), 11 deletions(-) (limited to 'strings.c') diff --git a/demo_functionality.c b/demo_functionality.c index 051ffd6..7a9139c 100644 --- a/demo_functionality.c +++ b/demo_functionality.c @@ -110,17 +110,6 @@ void demo_setup_PL0(void) puts("copied PL0 code to it's section"); } -// needed for array initialization in demo_go_unprivileged() -void *memset(void *s, int c, size_t n) -{ - char *mem = s; - - for (size_t i = 0; i < n; i++) - mem[i] = c; - - return s; -} - void demo_go_unprivileged(void) { uint32_t PL0_regs[14] = {0}; diff --git a/strings.c b/strings.c index 94cb6ac..b518388 100644 --- a/strings.c +++ b/strings.c @@ -91,3 +91,18 @@ void memcpy(void *dst, void *src, size_t nbytes) for (iter *= 4; iter < nbytes; iter++) ((volatile uint8_t*) dst)[iter] = ((uint8_t*) src)[iter]; } + +// keep in mind memset is also needed for array initialization, like +// uint32_t buf[16] = {0}; +// gcc compiles this to memset call + +void *memset(void *s, int c, size_t n) +{ + volatile char *mem = s; + + for (size_t i = 0; i < n; i++) + mem[i] = c; + + return s; +} + diff --git a/strings.h b/strings.h index 1eb291c..3c49b7e 100644 --- a/strings.h +++ b/strings.h @@ -26,4 +26,6 @@ size_t strlen(char string[]); void memcpy(void *dst, void *src, size_t nbytes); +void *memset(void *s, int c, size_t n); + #endif // STRINGS_H -- cgit v1.2.3 From b77ef684b07bcd91c168b15f71611786dd5a3377 Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Tue, 31 Dec 2019 17:28:49 +0100 Subject: add strcat --- strings.c | 15 +++++++++++++++ strings.h | 2 ++ 2 files changed, 17 insertions(+) (limited to 'strings.c') diff --git a/strings.c b/strings.c index b518388..c741938 100644 --- a/strings.c +++ b/strings.c @@ -106,3 +106,18 @@ void *memset(void *s, int c, size_t n) return s; } +char *strcat(char *dst, const char *src) +{ + char *where_to_append; + + for (where_to_append = dst; *where_to_append; where_to_append++); + + size_t i; + + for (i = 0; src[i]; i++) + ((char volatile*) where_to_append)[i] = src[i]; + + ((char volatile*) where_to_append)[i] = '\0'; + + return dst; +} diff --git a/strings.h b/strings.h index 3c49b7e..aff0533 100644 --- a/strings.h +++ b/strings.h @@ -28,4 +28,6 @@ void memcpy(void *dst, void *src, size_t nbytes); void *memset(void *s, int c, size_t n); +char *strcat(char *dst, const char *src); + #endif // STRINGS_H -- cgit v1.2.3 From 263a2ddec4f7f17c5bcd3a36ded396f6fe4e836a Mon Sep 17 00:00:00 2001 From: Wojtek Kosior Date: Tue, 31 Dec 2019 21:56:20 +0100 Subject: copy by one byte in memcpy to avoid alignment faults --- strings.c | 10 +++------- 1 file changed, 3 insertions(+), 7 deletions(-) (limited to 'strings.c') diff --git a/strings.c b/strings.c index c741938..368d7dc 100644 --- a/strings.c +++ b/strings.c @@ -82,13 +82,9 @@ void memcpy(void *dst, void *src, size_t nbytes) { size_t iter; - // copying by word is faster than by byte - // copy by word as much as possible - for (iter = 0; iter < nbytes / 4; iter++) - ((volatile uint32_t*) dst)[iter] = ((uint32_t*) src)[iter]; - - // copy the remaining 1, 2 or 3 bytes by byte - for (iter *= 4; iter < nbytes; iter++) + // copying by word is faster than by byte, + // but can easily cause alignment faults, so we resign from it... + for (iter = 0; iter < nbytes ; iter++) ((volatile uint8_t*) dst)[iter] = ((uint8_t*) src)[iter]; } -- cgit v1.2.3