88 else if (curr !=
next) {
95 if (ret_str[0] ==
'"' && ret_str[curr - 1] ==
'"') {
96 return ret_str.
substr(1, curr - 2);
98 return ret_str.
substr(0, curr);
104 for (
i = 0;
i <
sizeof(value);
i++) {
105 bytes[
i] = char((value >> (
int(
i) * 8)) & 0xff);
113 memcpy(bytes, msg.c_str(),
size);
129 Item(
const MapItem &other) : key(other.key), value(other.value) {}
130 Item(
const Item &other) =
default;
131 Item &
operator=(
const Item &other) =
default;
133 const uint32_t num_keys = messages.
size();
137 for (
const auto message_items_iter : messages.
items()) {
138 items.
append(Item(message_items_iter));
140 std::sort(items.
begin(), items.
end(), [](
const Item &a,
const Item &
b) ->
bool {
141 return a.key < b.key;
145 uint32_t tot_keys_len = 0;
146 uint32_t tot_vals_len = 0;
148 for (
int i = 0;
i < num_keys;
i++) {
155 tot_keys_len += off.
key_len + 1;
159 tot_vals_len += off.
val_len + 1;
164 const uint32_t idx_keystart = 7 * 4;
165 const uint32_t idx_valstart = idx_keystart + 8 * num_keys;
167 const uint32_t keystart = idx_valstart + 8 * num_keys;
169 const uint32_t valstart = keystart + tot_keys_len;
172 *r_output_size = valstart + tot_vals_len;
175 char *ik =
output + idx_keystart;
176 char *iv =
output + idx_valstart;
177 char *k =
output + keystart;
190 for (
int i = 0;
i < num_keys;
i++) {
191 const Offset &off = offsets[
i];
226 if (msg.
ctxt.empty()) {
227 msgkey = std::move(msg.
id);
231 msgkey = msg.
ctxt +
"\x04" + msg.
id;
234 messages.
add(std::move(msgkey), std::move(msg.
str));
239static int make(
const char *input_file_name,
const char *output_file_name)
243 const char *msgctxt_kw =
"msgctxt";
244 const char *msgid_kw =
"msgid";
245 const char *msgid_plural_kw =
"msgid_plural";
246 const char *msgstr_kw =
"msgstr";
247 const size_t msgctxt_len = strlen(msgctxt_kw);
248 const size_t msgid_len = strlen(msgid_kw);
249 const size_t msgid_plural_len = strlen(msgid_plural_kw);
250 const size_t msgstr_len = strlen(msgstr_kw);
255 bool is_plural =
false;
263 for (
int lno = 1; ifl; ifl = ifl->
next, lno++) {
264 std::string line =
static_cast<char *
>(ifl->
link);
269 const bool is_comment = (
l[0] ==
'#');
283 if (
l.startswith(msgctxt_kw)) {
289 printf(
"msgctxt not at start of new message on %s:%d\n", input_file_name, lno);
293 l =
l.substr(msgctxt_len);
296 else if (
l.startswith(msgid_plural_kw)) {
299 printf(
"msgid_plural not preceded by msgid on %s:%d\n", input_file_name, lno);
302 l =
l.substr(msgid_plural_len);
306 else if (
l.startswith(msgid_kw)) {
314 l =
l.substr(msgid_len);
317 else if (
l.startswith(msgstr_kw)) {
318 l =
l.substr(msgstr_len);
323 printf(
"plural without msgid_plural on %s:%d\n", input_file_name, lno);
326 int64_t close_bracket_idx =
l.find(
']');
328 printf(
"Syntax error on %s:%d\n", input_file_name, lno);
331 l =
l.substr(close_bracket_idx + 1);
332 if (!msg.
str.empty()) {
338 printf(
"indexed msgstr required for plural on %s:%d\n", input_file_name, lno);
364 printf(
"Syntax error on %s:%d\n", input_file_name, lno);
379 FILE *fp =
BLI_fopen(output_file_name,
"wb");
380 fwrite(
output, 1, output_size, fp);
391 printf(
"Usage: %s <input.po> <output.mo>\n", argv[0]);
394 const char *input_file = argv[1];
395 const char *output_file = argv[2];
397 return make(input_file, output_file);
File and directory operations.
FILE * BLI_fopen(const char *filepath, const char *mode) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
struct LinkNode * BLI_file_read_as_lines(const char *filepath) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
void BLI_file_free_lines(struct LinkNode *lines)
Read Guarded memory(de)allocation.
ATTR_WARN_UNUSED_RESULT const BMLoop * l
ATTR_WARN_UNUSED_RESULT const BMVert * v
static DBVT_INLINE btScalar size(const btDbvtVolume &a)
btGeneric6DofConstraint & operator=(btGeneric6DofConstraint &other)
MutableMapItem< Key, Value > MutableItem
bool add(const Key &key, const Value &value)
ItemIterator items() const &
static constexpr int64_t not_found
constexpr StringRef substr(int64_t start, int64_t size) const
void append(const T &value)
void * MEM_calloc_arrayN(size_t len, size_t size, const char *str)
void MEM_freeN(void *vmemh)
BLI_INLINE size_t uint32_to_bytes(const int value, char *bytes)
static void clear(Message &msg)
static int make(const char *input_file_name, const char *output_file_name)
static void add(blender::Map< std::string, std::string > &messages, Message &msg)
static char * generate(blender::Map< std::string, std::string > &messages, size_t *r_output_size)
static blender::StringRef unescape(std::string &str)
BLI_INLINE size_t msg_to_bytes(const std::string &msg, char *bytes, uint32_t size)