-
-/*
- * fmt_scan.c -- format string interpretation
+/* fmt_scan.c -- format string interpretation
*
* This code is Copyright (c) 2002, by the authors of nmh. See the
* COPYRIGHT file in the root directory of the nmh distribution for
#include <h/tws.h>
#include <h/fmt_compile.h>
#include <h/utils.h>
+#include "unquote.h"
#ifdef HAVE_SYS_TIME_H
# include <sys/time.h>
char *s1, *s2;
while ((c1 = *sub)) {
- c1 = (isascii((unsigned char) c1) && isalpha((unsigned char) c1) &&
- isupper((unsigned char) c1)) ? tolower((unsigned char) c1) : c1;
- while ((c2 = *str++) && c1 != ((isascii((unsigned char) c2) &&
- isalpha((unsigned char) c2) &&
- isupper((unsigned char) c2)) ?
- tolower((unsigned char) c2) : c2))
+ c1 = tolower((unsigned char)c1);
+ while ((c2 = *str++) && c1 != tolower((unsigned char)c2))
;
if (! c2)
return 0;
s1 = sub + 1; s2 = str;
- while ((c1 = *s1++) && ((isascii((unsigned char) c1) &&
- isalpha((unsigned char) c1) &&
- isupper((unsigned char) c1)) ?
- tolower(c1) : c1) ==
- ((isascii((unsigned char) (c2 =*s2++)) &&
- isalpha((unsigned char) c2) &&
- isupper((unsigned char) c2)) ?
- tolower((unsigned char) c2) : c2))
+ while ((c1 = *s1++) &&
+ tolower((unsigned char)c1) == tolower((unsigned char)(c2 = *s2++)))
;
if (! c1)
return 1;
cptrimmed(charstring_t dest, char *str, int wid, char fill, size_t max) {
int remaining; /* remaining output width available */
int rjust;
+ struct charstring *trimmed;
size_t end; /* number of input bytes remaining in str */
#ifdef MULTIBYTE_SUPPORT
int char_len; /* bytes in current character */
}
if (remaining > (int) max) { remaining = max; }
+ trimmed = rjust ? charstring_create(remaining) : dest;
+
if ((sp = str)) {
#ifdef MULTIBYTE_SUPPORT
if (mbtowc(NULL, NULL, 0)) {} /* reset shift state */
sp++;
#endif
if (!prevCtrl) {
- charstring_push_back (dest, ' ');
+ charstring_push_back (trimmed, ' ');
remaining--;
}
#ifdef MULTIBYTE_SUPPORT
if (w >= 0 && remaining >= w) {
- charstring_push_back_chars (dest, altstr ? altstr : sp,
+ charstring_push_back_chars (trimmed, altstr ? altstr : sp,
char_len, w);
remaining -= w;
altstr = NULL;
}
sp += char_len;
#else
- charstring_push_back (dest, *sp++);
+ charstring_push_back (trimmed, *sp++);
remaining--;
#endif
}
}
- if (rjust) {
- if (remaining > 0) {
- /* copy string to the right */
- charstring_t copy = charstring_copy (dest);
-
- /* add padding at the beginning */
- charstring_clear (dest);
- for (; remaining > 0; --remaining) {
- charstring_push_back (dest, fill);
- }
-
- charstring_append (dest, copy);
+ while (remaining-- > 0) {
+ charstring_push_back(dest, fill);
+ }
- charstring_free (copy);
- }
- } else {
- /* pad remaining space */
- while (remaining-- > 0) {
- charstring_push_back (dest, fill);
- }
+ if (rjust) {
+ charstring_append(dest, trimmed);
+ charstring_free(trimmed);
}
}
while (*str != '\0' && len > 0 && max > 0) {
#ifdef MULTIBYTE_SUPPORT
char_len = mbtowc(&wide_char, str, len);
- w = wcwidth(wide_char);
/*
* If mbrtowc() failed, then we have a character that isn't valid
- * in the current encoding. Replace it with a '?'. We do that by
+ * in the current encoding, or len wasn't enough for the whole
+ * multi-byte rune to be read. Replace it with a '?'. We do that by
* setting the alstr variable to the value of the replacement string;
* altstr is used below when the bytes are copied into the output
* buffer.
*/
-
if (char_len < 0) {
altstr = "?";
char_len = mbtowc(&wide_char, altstr, 1);
prevCtrl = 0;
#ifdef MULTIBYTE_SUPPORT
- charstring_push_back_chars (dest, altstr ? altstr : str, char_len, w);
- max -= w;
- str += char_len;
- altstr = NULL;
+ w = wcwidth(wide_char);
+ assert(w >= 0);
+ if (max >= (size_t) w) {
+ charstring_push_back_chars (dest, altstr ? altstr : str, char_len, w);
+ max -= w;
+ str += char_len;
+ altstr = NULL;
+ } else {
+ /* Not enough width available for the last character. Output
+ space(s) to fill. */
+ while (max-- > 0) {
+ charstring_push_back (dest, ' ');
+ }
+ break;
+ }
#else /* MULTIBYE_SUPPORT */
charstring_push_back (dest, *str++);
--max;
{
char *sp;
char *savestr, *str;
- char buffer[BUFSIZ], buffer2[BUFSIZ];
+ char buffer[NMH_BUFSIZ], buffer2[NMH_BUFSIZ];
int i, c, rjust;
int value;
time_t t;
int num = value;
unsigned int wid;
- for (wid = num <= 0 ? 1 : 0; num; ++wid, num /= 10) {}
+ for (wid = num <= 0; num; ++wid, num /= 10) {}
cpnumber (scanlp, value, wid, ' ',
max - charstring_chars (scanlp));
break;
break;
case FT_LV_DIVIDE_L:
if (fmt->f_value)
- value = value / fmt->f_value;
+ value /= fmt->f_value;
else
value = 0;
break;
case FT_LV_MODULO_L:
if (fmt->f_value)
- value = value % fmt->f_value;
+ value %= fmt->f_value;
else
value = 0;
break;
}
break;
case FT_LV_ZONEF:
- if ((fmt->f_comp->c_tws->tw_flags & TW_SZONE) == TW_SZEXP)
+ if (fmt->f_comp->c_tws->tw_flags & TW_SZEXP)
value = 1;
else
value = -1;