diff --git a/include/unicode.h b/include/unicode.h index e2ee958..56a48f1 100644 --- a/include/unicode.h +++ b/include/unicode.h @@ -9,6 +9,14 @@ #define UTF8_INVALID 0x80 +/** + * Gets the size in bytes of the last utf8 character in a NULL terminated string + * This function does not validate that the buffer contains correct utf8 data; + * it merely looks for the first byte that correctly denotes the beginning of a + * utf8 character. + */ +int utf8_last_size(const char *str); + /** * Grabs the next UTF-8 character and advances the string pointer */ diff --git a/password.c b/password.c index e1a1d9a..6880ccb 100644 --- a/password.c +++ b/password.c @@ -28,7 +28,8 @@ void clear_password_buffer(struct swaylock_password *pw) { static bool backspace(struct swaylock_password *pw) { if (pw->len != 0) { - pw->buffer[--pw->len] = 0; + pw->len -= utf8_last_size(pw->buffer); + pw->buffer[pw->len] = 0; return true; } return false; diff --git a/unicode.c b/unicode.c index 3d81a34..6d115a9 100644 --- a/unicode.c +++ b/unicode.c @@ -1,7 +1,20 @@ #include #include +#include #include "unicode.h" +int utf8_last_size(const char *str) { + int len = 0; + char *pos = strchr(str, '\0'); + while (pos > str) { + --pos; ++len; + if ((*pos & 0xc0) != 0x80) { + return len; + } + } + return 0; +} + size_t utf8_chsize(uint32_t ch) { if (ch < 0x80) { return 1;