diff --git a/all.h b/all.h index 780f2b4..3a73e55 100644 --- a/all.h +++ b/all.h @@ -351,6 +351,7 @@ typedef struct StringUTF16Const { } StringUTF16Const; typedef enum Utf8Character { + Utf8CharacterInvalid = 0, Utf8CharacterAscii, Utf8CharacterTwoByte, Utf8CharacterThreeByte, diff --git a/string.c b/string.c index dba0eae..53b76e3 100644 --- a/string.c +++ b/string.c @@ -38,7 +38,7 @@ fn Utf8Character utf8CharacterClassify(u8 c) { return Utf8CharacterFourByte; } else { assert(false && "Not a valid utf8 starting byte"); - return Utf8Character_Count; + return Utf8CharacterInvalid; } } @@ -55,7 +55,7 @@ fn Utf8Character utf8CharacterClassifyUnsafe(u8 c) { } else if (c >= 240) { return Utf8CharacterFourByte; } else { - return Utf8Character_Count; + return Utf8CharacterInvalid; } } @@ -115,29 +115,27 @@ fn bool codepointIsWhitespace(Codepoint c) { fn Codepoint codepointFromBytes(ptr bytes, u32 offset) { Codepoint result = {0}; result.type = utf8CharacterClassify(bytes[offset]); + result.size = result.type; switch (result.type) { case Utf8CharacterAscii: { - result.size = 1; result.code = bytes[offset]; } break; case Utf8CharacterTwoByte: { - result.size = 2; result.code = ( bytes[offset] << 8 | bytes[offset+1] ); } break; case Utf8CharacterThreeByte: { - result.size = 3; result.code = ( bytes[offset] << 16 | bytes[offset+1] << 8 | bytes[offset+2] ); } break; case Utf8CharacterFourByte: { - result.size = 4; result.code = ( bytes[offset] << 24 | bytes[offset+1] << 16 | bytes[offset+2] << 8 | bytes[offset+3] ); } break; + case Utf8CharacterInvalid: case Utf8Character_Count: { printf("unabled to classify utf8 codepoint %d\n", bytes[offset]); assert(false); @@ -148,36 +146,34 @@ fn Codepoint codepointFromBytes(ptr bytes, u32 offset) { fn Codepoint codepointFromBytesBefore(ptr bytes, u32 offset) { assert(offset > 0); - Codepoint result = { .type = Utf8Character_Count }; + Codepoint result = { .type = Utf8CharacterInvalid }; u32 i = 0; - while (result.type == Utf8Character_Count && i <= 4) { + while (result.type == Utf8CharacterInvalid && i <= 4) { i++; offset -= 1; result.type = utf8CharacterClassifyUnsafe(bytes[offset]); } + result.size = result.type; switch (result.type) { case Utf8CharacterAscii: { - result.size = 1; result.code = bytes[offset]; } break; case Utf8CharacterTwoByte: { - result.size = 2; result.code = ( bytes[offset] << 8 | bytes[offset+1] ); } break; case Utf8CharacterThreeByte: { - result.size = 3; result.code = ( bytes[offset] << 16 | bytes[offset+1] << 8 | bytes[offset+2] ); } break; case Utf8CharacterFourByte: { - result.size = 4; result.code = ( bytes[offset] << 24 | bytes[offset+1] << 16 | bytes[offset+2] << 8 | bytes[offset+3] ); } break; + case Utf8CharacterInvalid: case Utf8Character_Count: { printf("unabled to classify utf8 codepoint %d\n", bytes[offset]); assert(false); @@ -224,6 +220,7 @@ fn void codepointFillBuf(Codepoint cp, ptr buf) { buf[2] = (cp.code & 0xFF00) >> 8; buf[3] = cp.code & 0xFF; } break; + case Utf8CharacterInvalid: case Utf8Character_Count: { assert(false); } break; @@ -233,15 +230,9 @@ fn void codepointFillBuf(Codepoint cp, ptr buf) { fn String stringFromRawCodepoint(Arena* a, u32 c) { String result = {0}; Codepoint codepoint = codepointFromRawInt(c); - switch (codepoint.type) { - case Utf8CharacterAscii: result.capacity = 1; break; - case Utf8CharacterTwoByte: result.capacity = 2; break; - case Utf8CharacterThreeByte: result.capacity = 3; break; - case Utf8CharacterFourByte: result.capacity = 4; break; - case Utf8Character_Count: { - assert(false); - } break; - } + assert(codepoint.type != Utf8Character_Count); + assert(codepoint.type != Utf8CharacterInvalid); + result.capacity = codepoint.size; result.length = result.capacity; result.bytes = arenaAlloc(a, result.length); codepointFillBuf(codepoint, result.bytes);