hnj_hyphen_hyphword: rewrite, improve overflow checking

This commit is contained in:
Bartek Fabiszewski 2017-04-26 22:39:07 +02:00
parent 6962afb690
commit 4e09ea69d6
1 changed files with 31 additions and 15 deletions

View File

@ -39,6 +39,7 @@
#include <stdlib.h> /* for NULL, malloc */
#include <stdio.h> /* for fprintf */
#include <string.h> /* for strdup */
#include <limits.h> /* for INT_MAX */
#ifdef UNX
#include <unistd.h> /* for exit */
@ -1073,26 +1074,41 @@ int hnj_hyphen_norm(const char *word, int word_size, char * hyphens,
}
/* get the word with all possible hyphenations (output: hyphword) */
void hnj_hyphen_hyphword(const char * word, int l, const char * hyphens,
void hnj_hyphen_hyphword(const char * word, int word_size, const char * hyphens,
char * hyphword, char *** rep, int ** pos, int ** cut)
{
if (word_size <= 0 || word_size > INT_MAX / 2) {
hyphword[0] = '\0';
return;
}
/* hyphword buffer size must be at least 2 * l */
int hyphword_len = 2 * l - 1;
int hyphword_size = 2 * word_size - 1;
int i, j;
for (i = 0, j = 0; i < l && j < hyphword_len; i++, j++) {
if (hyphens[i]&1) {
hyphword[j] = word[i];
if (*rep && *pos && *cut && (*rep)[i]) {
j -= (*pos)[i] - 1;
size_t rep_len = strlen((*rep)[i]);
if (j + rep_len > hyphword_len)
break;
strcpy(hyphword + j, (*rep)[i]);
j += rep_len - 1;
int nonstandard = 0;
if (*rep && *pos && *cut) {
nonstandard = 1;
}
int i;
int j = 0;
for (i = 0; i < word_size && j < hyphword_size; i++) {
hyphword[j++] = word[i];
if (hyphens[i]&1 && j < hyphword_size) {
if (nonstandard && (*rep)[i] && j >= (*pos)[i]) {
/* non-standard */
j -= (*pos)[i];
char *s = (*rep)[i];
while (*s && j < hyphword_size) {
hyphword[j++] = *s++;
}
i += (*cut)[i] - (*pos)[i];
} else hyphword[++j] = '=';
} else hyphword[j] = word[i];
} else {
/* standard */
hyphword[j++] = '=';
}
}
}
hyphword[j] = '\0';
}