summaryrefslogtreecommitdiffstats
path: root/bin
diff options
context:
space:
mode:
authorjilles <jilles@FreeBSD.org>2011-05-07 14:32:16 +0000
committerjilles <jilles@FreeBSD.org>2011-05-07 14:32:16 +0000
commit8bbce85526c337676cfa1f717dac02d86742cf0a (patch)
tree56cf1ceba22fd77045407a8fa8188f0feeecf4b6 /bin
parent11604ee85b5b347285de99920d04978997c18508 (diff)
downloadFreeBSD-src-8bbce85526c337676cfa1f717dac02d86742cf0a.zip
FreeBSD-src-8bbce85526c337676cfa1f717dac02d86742cf0a.tar.gz
sh: Add UTF-8 support to ${#var}.
If the current locale uses UTF-8, ${#var} counts codepoints (more precisely, bytes b with (b & 0xc0) != 0x80).
Diffstat (limited to 'bin')
-rw-r--r--bin/sh/expand.c16
1 files changed, 13 insertions, 3 deletions
diff --git a/bin/sh/expand.c b/bin/sh/expand.c
index c343977..dcef74e 100644
--- a/bin/sh/expand.c
+++ b/bin/sh/expand.c
@@ -665,6 +665,7 @@ evalvar(char *p, int flag)
int special;
int startloc;
int varlen;
+ int varlenb;
int easy;
int quotes = flag & (EXP_FULL | EXP_CASE | EXP_REDIR);
@@ -712,8 +713,15 @@ again: /* jump here after setting a variable with ${var=text} */
if (special) {
varvalue(var, varflags & VSQUOTE, subtype, flag);
if (subtype == VSLENGTH) {
- varlen = expdest - stackblock() - startloc;
- STADJUST(-varlen, expdest);
+ varlenb = expdest - stackblock() - startloc;
+ varlen = varlenb;
+ if (localeisutf8) {
+ val = stackblock() + startloc;
+ for (;val != expdest; val++)
+ if ((*val & 0xC0) == 0x80)
+ varlen--;
+ }
+ STADJUST(-varlenb, expdest);
}
} else {
char const *syntax = (varflags & VSQUOTE) ? DQSYNTAX
@@ -721,7 +729,9 @@ again: /* jump here after setting a variable with ${var=text} */
if (subtype == VSLENGTH) {
for (;*val; val++)
- varlen++;
+ if (!localeisutf8 ||
+ (*val & 0xC0) != 0x80)
+ varlen++;
}
else {
if (quotes)
OpenPOWER on IntegriCloud