Skip to content

Commit 64810a3

Browse files
committed
🛠 fight tooth and nail with the stupid win32
1 parent 19e6a7d commit 64810a3

File tree

8 files changed

+989
-411
lines changed

8 files changed

+989
-411
lines changed

documentation/Doxyfile.in

Lines changed: 497 additions & 297 deletions
Large diffs are not rendered by default.
Lines changed: 157 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,157 @@
1+
// ============================================================================
2+
//
3+
// ztd.cuneicode
4+
// Copyright © JeanHeyd "ThePhD" Meneide and Shepherd's Oasis, LLC
5+
// Contact: opensource@soasis.org
6+
//
7+
// Commercial License Usage
8+
// Licensees holding valid commercial ztd.cuneicode licenses may use this file
9+
// in accordance with the commercial license agreement provided with the
10+
// Software or, alternatively, in accordance with the terms contained in
11+
// a written agreement between you and Shepherd's Oasis, LLC.
12+
// For licensing terms and conditions see your agreement. For
13+
// further information contact opensource@soasis.org.
14+
//
15+
// Apache License Version 2 Usage
16+
// Alternatively, this file may be used under the terms of Apache License
17+
// Version 2.0 (the "License"); you may not use this file except in compliance
18+
// with the License. You may obtain a copy of the License at
19+
//
20+
// https://www.apache.org/licenses/LICENSE-2.0
21+
//
22+
// Unless required by applicable law or agreed to in writing, software
23+
// distributed under the License is distributed on an "AS IS" BASIS,
24+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
25+
// See the License for the specific language governing permissions and
26+
// limitations under the License.
27+
//
28+
// ========================================================================= //
29+
30+
#define _CRT_SECURE_NO_WARNINGS
31+
32+
#include <ztd/cuneicode.h>
33+
34+
#include <ztd/idk/size.h>
35+
36+
#include <stdio.h>
37+
#include <stdint.h>
38+
#include <stdbool.h>
39+
#include <string.h>
40+
41+
#if ZTD_IS_ON(ZTD_PLATFORM_WINDOWS)
42+
43+
int main(int argc, char* argv[]) {
44+
const char* const failed_conversion_result_title_str
45+
= "Conversion failed... \xF0\x9F\x98\xAD"; // UTF-8 bytes for 😭
46+
const char* const success_conversion_result_title_str
47+
= "Conversion succeeded \xF0\x9F\x8E\x89"; // UTF-8 bytes for 🎉
48+
const size_t success_conversion_result_title_str_size
49+
= strlen(success_conversion_result_title_str);
50+
const size_t failed_conversion_result_title_str_size
51+
= strlen(failed_conversion_result_title_str);
52+
(void)argc;
53+
(void)argv;
54+
const ztd_char32_t input_data[]
55+
= U"ସମସ୍ତ ମନୁଷ୍ୟ ଜନ୍ମକାଳରୁ ସ୍ଧୀନ ଏବଂ ମର୍ଯ୍ୟାଦା ଓ ଅଧିକାରରେ ସମାନ. ସେମାନଙ୍କଠାରେ ବୁଦ୍ଧି "
56+
U"ଆଉ ବିବେକ ନିହିତ ଅଛି ଏବଂ ସେମାନଙ୍କୁ ପରସ୍ପର ପ୍ରତି ଭ୍ରାତୃତ୍ ମନୋଭାବରେ ବ୍ୟବହାର କରିବା ଉଚିତ୍";
57+
const uint32_t win32_odia_code_page = 57007u;
58+
char intermediate_data[ztdc_c_array_size(input_data) * CNC_MC_MAX] = { 0 };
59+
cnc_mcstate_t intermediate_state = { 0 };
60+
61+
cnc_mcstate_set_win32_code_page(&intermediate_state, win32_odia_code_page);
62+
const size_t starting_input_size = ztdc_c_string_array_size(input_data);
63+
size_t input_size = starting_input_size;
64+
const ztd_char32_t* input = input_data;
65+
const size_t starting_intermediate_size
66+
= ztdc_c_array_size(intermediate_data);
67+
size_t intermediate_size = starting_intermediate_size;
68+
char* intermediate = intermediate_data;
69+
cnc_mcerr intermediate_err
70+
= cnc_c32snrtomcsn_windows_code_page(&intermediate_size, &intermediate,
71+
&input_size, &input, &intermediate_state);
72+
const size_t input_read = starting_input_size - input_size;
73+
const size_t intermediate_written
74+
= starting_intermediate_size - intermediate_size;
75+
76+
if (intermediate_err != cnc_mcerr_ok) {
77+
// failed initial conversion
78+
// Use fwrite to prevent conversions / locale-sensitive-probing from
79+
// fprintf family of functions
80+
fprintf(stderr, "Intermediate conversion:\n");
81+
fwrite(failed_conversion_result_title_str,
82+
sizeof(*failed_conversion_result_title_str),
83+
failed_conversion_result_title_str_size, stderr);
84+
fprintf(stderr,
85+
"\n\tRead: %zu %zu-bit elements"
86+
"\n\tWrote: %zu %zu-bit elements\n\n",
87+
(size_t)(input_read), (size_t)(sizeof(*input) * CHAR_BIT),
88+
(size_t)(intermediate_written),
89+
(size_t)(sizeof(*intermediate) * CHAR_BIT));
90+
return 1;
91+
}
92+
else {
93+
fprintf(stdout, "Intermediate conversion:\n");
94+
fwrite(success_conversion_result_title_str,
95+
sizeof(*success_conversion_result_title_str),
96+
success_conversion_result_title_str_size, stdout);
97+
fprintf(stdout,
98+
"\n\tRead: %zu %zu-bit elements"
99+
"\n\tWrote: %zu %zu-bit elements\n\n",
100+
(size_t)(input_read), (size_t)(sizeof(*input) * CHAR_BIT),
101+
(size_t)(intermediate_written),
102+
(size_t)(sizeof(*intermediate) * CHAR_BIT));
103+
}
104+
105+
ztd_char32_t output_data[ztdc_c_array_size(input_data)] = { 0 };
106+
cnc_mcstate_t state = { 0 };
107+
cnc_mcstate_set_win32_code_page(&state, win32_odia_code_page);
108+
size_t intermediate_input_size = intermediate_written;
109+
const char* intermediate_input = intermediate_data;
110+
const size_t starting_output_size = ztdc_c_array_size(output_data);
111+
size_t output_size = starting_output_size;
112+
ztd_char32_t* output = output_data;
113+
cnc_mcerr err = cnc_mcsnrtoc32sn_windows_code_page(&output_size, &output,
114+
&intermediate_input_size, &intermediate_input, &state);
115+
const size_t intermediate_read
116+
= intermediate_written - intermediate_input_size;
117+
const size_t output_written = starting_output_size - output_size;
118+
if (err != cnc_mcerr_ok) {
119+
// failed back to the original
120+
fprintf(stderr, "Output conversion:\n");
121+
fwrite(failed_conversion_result_title_str,
122+
sizeof(*failed_conversion_result_title_str),
123+
failed_conversion_result_title_str_size, stderr);
124+
fprintf(stderr,
125+
"\n\tRead: %zu %zu-bit elements"
126+
"\n\tWrote: %zu %zu-bit elements\n\n",
127+
(size_t)(intermediate_read),
128+
(size_t)(sizeof(*intermediate) * CHAR_BIT),
129+
(size_t)(output_written), (size_t)(sizeof(*output) * CHAR_BIT));
130+
return 2;
131+
}
132+
else {
133+
fprintf(stdout, "Output conversion:\n");
134+
fwrite(success_conversion_result_title_str,
135+
sizeof(*success_conversion_result_title_str),
136+
success_conversion_result_title_str_size, stdout);
137+
fprintf(stdout,
138+
"\n\tRead: %zu %zu-bit elements"
139+
"\n\tWrote: %zu %zu-bit elements\n\n",
140+
(size_t)(intermediate_read),
141+
(size_t)(sizeof(*intermediate) * CHAR_BIT),
142+
(size_t)(output_written), (size_t)(sizeof(*output) * CHAR_BIT));
143+
}
144+
145+
return 0;
146+
}
147+
148+
#else
149+
150+
int main(int argc, char* argv[]) {
151+
// does not work on this platform
152+
(void)argc;
153+
(void)argv;
154+
return 0;
155+
}
156+
157+
#endif

include/ztd/cuneicode/mcstate.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@
3535
#include <ztd/cuneicode/version.h>
3636

3737
#include <ztd/idk/mbstate_t.h>
38+
#include <ztd/idk/charN_t.h>
3839

3940
#if ZTD_IS_ON(ZTD_CXX)
4041
#include <cstddef>
@@ -159,6 +160,14 @@ typedef union cnc_mcstate_t {
159160
//////
160161
/// @brief Private, do not access.
161162
uint32_t __code_page;
163+
//////
164+
/// @brief Private, do not access.
165+
union {
166+
ztd_wchar_t __wide_accumulator[(sizeof(ztd_mbstate_t) * 2 - sizeof(uint32_t))
167+
/ sizeof(ztd_wchar_t)];
168+
char __narrow_accumulator[(sizeof(ztd_mbstate_t) * 2 - sizeof(uint32_t))
169+
/ sizeof(char)];
170+
};
162171
} __win32_code_page;
163172
//////
164173
/// @brief The raw type for user use.

include/ztd/cuneicode/registry.h

Lines changed: 18 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -440,7 +440,6 @@ cnc_open_err cnc_registry_add(cnc_conversion_registry* __registry, const ztd_cha
440440
/// `__to`, respectively. If `__from` or
441441
/// `__to` are `nullptr`, then the function will assume they are the empty string (and use the
442442
/// default name in that case).
443-
///////
444443
ZTD_USE(ZTD_C_LANGUAGE_LINKAGE)
445444
ZTD_USE(ZTD_CUNEICODE_API_LINKAGE)
446445
cnc_open_err cnc_registry_add_c8n_multimin(cnc_conversion_registry* __registry, size_t __from_size,
@@ -600,12 +599,12 @@ cnc_open_err cnc_registry_add_alias_n(cnc_conversion_registry* __registry, size_
600599
/// assume they are the empty string (and use the default name in that case).
601600
ZTD_USE(ZTD_C_LANGUAGE_LINKAGE)
602601
ZTD_USE(ZTD_CUNEICODE_API_LINKAGE)
603-
cnc_open_err
604-
cnc_registry_add_multi_c8(cnc_conversion_registry* __registry, const ztd_char8_t* __from,
605-
const ztd_char8_t* __to, cnc_conversion_function* __multi_conversion_function,
606-
cnc_state_is_complete_function* __state_is_complete_function,
607-
cnc_open_function* __open_function, cnc_close_function* __close_function)
608-
ZTD_USE(ZTD_NOEXCEPT_IF_CXX);
602+
cnc_open_err cnc_registry_add_multi_c8(cnc_conversion_registry* __registry,
603+
const ztd_char8_t* __from, const ztd_char8_t* __to,
604+
cnc_conversion_function* __multi_conversion_function,
605+
cnc_state_is_complete_function* __state_is_complete_function,
606+
cnc_open_function* __open_function, cnc_close_function* __close_function)
607+
ZTD_USE(ZTD_NOEXCEPT_IF_CXX);
609608

610609
//////
611610
/// @copydoc cnc_registry_add_multi_c8
@@ -759,12 +758,12 @@ cnc_open_err cnc_registry_add_multi_c8_multimin(cnc_conversion_registry* __regis
759758
/// @copydoc cnc_registry_add_multi_c8_multimin
760759
ZTD_USE(ZTD_C_LANGUAGE_LINKAGE)
761760
ZTD_USE(ZTD_CUNEICODE_API_LINKAGE)
762-
cnc_open_err
763-
cnc_registry_add_multi_multimin(cnc_conversion_registry* __registry, const ztd_char_t* __from,
764-
const ztd_char_t* __to, cnc_conversion_function* __multi_conversion_function,
765-
cnc_state_is_complete_function* __state_is_complete_function,
766-
cnc_open_function* __open_function, cnc_close_function* __close_function,
767-
size_t __multi_conversion_minimum_byte_size) ZTD_USE(ZTD_NOEXCEPT_IF_CXX);
761+
cnc_open_err cnc_registry_add_multi_multimin(cnc_conversion_registry* __registry,
762+
const ztd_char_t* __from, const ztd_char_t* __to,
763+
cnc_conversion_function* __multi_conversion_function,
764+
cnc_state_is_complete_function* __state_is_complete_function,
765+
cnc_open_function* __open_function, cnc_close_function* __close_function,
766+
size_t __multi_conversion_minimum_byte_size) ZTD_USE(ZTD_NOEXCEPT_IF_CXX);
768767

769768
//////
770769
/// @brief Adds a new conversion from the specified `__from` and `__to` names to the specified
@@ -792,12 +791,12 @@ cnc_open_err
792791
/// assume they are the empty string (and use the default name in that case).
793792
ZTD_USE(ZTD_C_LANGUAGE_LINKAGE)
794793
ZTD_USE(ZTD_CUNEICODE_API_LINKAGE)
795-
cnc_open_err
796-
cnc_registry_add_single_c8(cnc_conversion_registry* __registry, const ztd_char8_t* __from,
797-
const ztd_char8_t* __to, cnc_conversion_function* __single_conversion_function,
798-
cnc_state_is_complete_function* __state_is_complete_function,
799-
cnc_open_function* __open_function, cnc_close_function* __close_function)
800-
ZTD_USE(ZTD_NOEXCEPT_IF_CXX);
794+
cnc_open_err cnc_registry_add_single_c8(cnc_conversion_registry* __registry,
795+
const ztd_char8_t* __from, const ztd_char8_t* __to,
796+
cnc_conversion_function* __single_conversion_function,
797+
cnc_state_is_complete_function* __state_is_complete_function,
798+
cnc_open_function* __open_function, cnc_close_function* __close_function)
799+
ZTD_USE(ZTD_NOEXCEPT_IF_CXX);
801800

802801
//////
803802
/// @copydoc cnc_registry_add_single_c8

0 commit comments

Comments
 (0)