diff --git a/qse/include/qse/cmn/str.h b/qse/include/qse/cmn/str.h
index 594f20dc..5e0f77ca 100644
--- a/qse/include/qse/cmn/str.h
+++ b/qse/include/qse/cmn/str.h
@@ -1,5 +1,5 @@
/*
- * $Id: str.h 416 2011-03-27 05:04:24Z hyunghwan.chung $
+ * $Id: str.h 417 2011-03-27 14:32:37Z hyunghwan.chung $
*
Copyright 2006-2009 Chung, Hyung-Hwan.
This file is part of QSE.
@@ -57,16 +57,32 @@ struct qse_str_t
};
/**
- * The qse_strxsubst_subst_t type defines a callback function
- * for qse_strxsubst() to substitue a new value for an identifier @a ident.
+ * The qse_mbsxsubst_subst_t type defines a callback function
+ * for qse_mbsxsubst() to substitue a new value for an identifier @a ident.
*/
-typedef qse_char_t* (*qse_strxsubst_subst_t) (
- qse_char_t* buf,
- qse_size_t bsz,
- const qse_cstr_t* ident,
- void* ctx
+typedef qse_mchar_t* (*qse_mbsxsubst_subst_t) (
+ qse_mchar_t* buf,
+ qse_size_t bsz,
+ const qse_mcstr_t* ident,
+ void* ctx
);
+/**
+ * The qse_wcsxsubst_subst_t type defines a callback function
+ * for qse_wcsxsubst() to substitue a new value for an identifier @a ident.
+ */
+typedef qse_wchar_t* (*qse_wcsxsubst_subst_t) (
+ qse_wchar_t* buf,
+ qse_size_t bsz,
+ const qse_wcstr_t* ident,
+ void* ctx
+);
+
+#ifdef QSE_CHAR_IS_MCHAR
+# define qse_strxsubst_subst_t qse_mbsxsubst_subst_t
+#else
+# define qse_strxsubst_subst_t qse_wcsxsubst_subst_t
+#endif
/* int qse_chartonum (qse_char_t c, int base) */
#define QSE_CHARTONUM(c,base) \
@@ -435,31 +451,63 @@ qse_size_t qse_wcsxfncpy (
#endif
/**
- * The qse_strxsubst() function expands @a fmt into a buffer @a buf of the size
+ * The qse_mbsxsubst() function expands @a fmt into a buffer @a buf of the size
* @a bsz by substituting new values for ${} segments within it. The actual
* substitution is made by invoking the callback function @a subst.
* @code
- * qse_char_t* subst (qse_char_t* buf, qse_size_t bsz, const qse_cstr_t* ident, void* ctx)
+ * qse_mchar_t* subst (qse_mchar_t* buf, qse_size_t bsz, const qse_mcstr_t* ident, void* ctx)
* {
- * if (qse_strxcmp (ident->ptr, ident->len, QSE_T("USER")) == 0)
- * return buf + qse_strxput (buf, bsz, QSE_T("sam"));
- * else if (qse_strxcmp (ident->ptr, ident->len, QSE_T("GROUP")) == 0)
- * return buf + qse_strxput (buf, bsz, QSE_T("coders"));
+ * if (qse_mbsxcmp (ident->ptr, ident->len, QSE_MT("USER")) == 0)
+ * return buf + qse_mbsxput (buf, bsz, QSE_MT("sam"));
+ * else if (qse_mbsxcmp (ident->ptr, ident->len, QSE_MT("GROUP")) == 0)
+ * return buf + qse_mbsxput (buf, bsz, QSE_MT("coders"));
* return buf;
* }
*
- * qse_char_t buf[25];
- * qse_strxsubst (buf, i, QSE_T("user=${USER},group=${GROUP}"), subst, QSE_NULL);
+ * qse_mchar_t buf[25];
+ * qse_mbsxsubst (buf, i, QSE_MT("user=${USER},group=${GROUP}"), subst, QSE_NULL);
* @endcode
*/
-qse_size_t qse_strxsubst (
- qse_char_t* buf,
+qse_size_t qse_mbsxsubst (
+ qse_mchar_t* buf,
qse_size_t bsz,
- const qse_char_t* fmt,
- qse_strxsubst_subst_t subst,
+ const qse_mchar_t* fmt,
+ qse_mbsxsubst_subst_t subst,
void* ctx
);
+/**
+ * The qse_wcsxsubst() function expands @a fmt into a buffer @a buf of the size
+ * @a bsz by substituting new values for ${} segments within it. The actual
+ * substitution is made by invoking the callback function @a subst.
+ * @code
+ * qse_wchar_t* subst (qse_wchar_t* buf, qse_size_t bsz, const qse_wcstr_t* ident, void* ctx)
+ * {
+ * if (qse_wcsxcmp (ident->ptr, ident->len, QSE_WT("USER")) == 0)
+ * return buf + qse_wcsxput (buf, bsz, QSE_WT("sam"));
+ * else if (qse_wcsxcmp (ident->ptr, ident->len, QSE_WT("GROUP")) == 0)
+ * return buf + qse_wcsxput (buf, bsz, QSE_WT("coders"));
+ * return buf;
+ * }
+ *
+ * qse_wchar_t buf[25];
+ * qse_wcsxsubst (buf, i, QSE_WT("user=${USER},group=${GROUP}"), subst, QSE_NULL);
+ * @endcode
+ */
+qse_size_t qse_wcsxsubst (
+ qse_wchar_t* buf,
+ qse_size_t bsz,
+ const qse_wchar_t* fmt,
+ qse_wcsxsubst_subst_t subst,
+ void* ctx
+);
+
+#ifdef QSE_CHAR_IS_MCHAR
+# define qse_strxsubst(buf,bsz,fmt,subst,ctx) qse_mbsxsubst(buf,bsz,fmt,subst,ctx)
+#else
+# define qse_strxsubst(buf,bsz,fmt,subst,ctx) qse_wcsxsubst(buf,bsz,fmt,subst,ctx)
+#endif
+
qse_size_t qse_strxcat (
qse_char_t* buf,
qse_size_t bsz,
@@ -713,11 +761,37 @@ qse_char_t* qse_strxnrstr (
qse_size_t subsz
);
+/**
+ * The qse_strxword() function finds a whole word in a string.
+ */
+const qse_char_t* qse_strxword (
+ const qse_char_t* str,
+ qse_size_t len,
+ const qse_char_t* word
+);
+
+/**
+ * The qse_strxcaseword() function finds a whole word in a string
+ * case-insensitively.
+ */
+const qse_char_t* qse_strxcaseword (
+ const qse_char_t* str,
+ qse_size_t len,
+ const qse_char_t* word
+);
+
+
+/**
+ * The qse_mbschr() function finds a chracter in a string.
+ */
qse_mchar_t* qse_mbschr (
const qse_mchar_t* str,
qse_mcint_t c
);
+/**
+ * The qse_wcschr() function finds a chracter in a string.
+ */
qse_wchar_t* qse_wcschr (
const qse_wchar_t* str,
qse_wcint_t c
@@ -769,26 +843,6 @@ qse_wchar_t* qse_wcsxrchr (
# define qse_strxrrchr(str,len,c) qse_wcsxrchr(str,len,c)
#endif
-
-/**
- * The qse_strxword() function finds a whole word in a string.
- */
-const qse_char_t* qse_strxword (
- const qse_char_t* str,
- qse_size_t len,
- const qse_char_t* word
-);
-
-/**
- * The qse_strxcaseword() function finds a whole word in a string
- * case-insensitively.
- */
-const qse_char_t* qse_strxcaseword (
- const qse_char_t* str,
- qse_size_t len,
- const qse_char_t* word
-);
-
/**
* The qse_strbeg() function checks if the a string begins with a substring.
* @return the pointer to a beginning of a matching beginning,
diff --git a/qse/lib/cmn/Makefile.am b/qse/lib/cmn/Makefile.am
index 68778d4f..92c95baa 100644
--- a/qse/lib/cmn/Makefile.am
+++ b/qse/lib/cmn/Makefile.am
@@ -10,7 +10,7 @@ libqsecmn_la_SOURCES = \
syscall.h mem.h \
mem.c xma.c fma.c chr.c chr_cnv.c rex.c \
str_bas.c str_chr.c str_cnv.c str_cmp.c str_cpy.c str_dyn.c str_fcpy.c \
- str_pbrk.c str_put.c str_spn.c str_utl.c \
+ str_pbrk.c str_put.c str_spn.c str_subst.c str_utl.c \
lda.c oht.c htb.c rbt.c sll.c gdl.c dll.c opt.c \
tio.c tio_get.c tio_put.c \
fio.c pio.c sio.c \
diff --git a/qse/lib/cmn/Makefile.in b/qse/lib/cmn/Makefile.in
index 9a1f1db0..3324000d 100644
--- a/qse/lib/cmn/Makefile.in
+++ b/qse/lib/cmn/Makefile.in
@@ -75,10 +75,10 @@ libqsecmn_la_DEPENDENCIES =
am_libqsecmn_la_OBJECTS = mem.lo xma.lo fma.lo chr.lo chr_cnv.lo \
rex.lo str_bas.lo str_chr.lo str_cnv.lo str_cmp.lo str_cpy.lo \
str_dyn.lo str_fcpy.lo str_pbrk.lo str_put.lo str_spn.lo \
- str_utl.lo lda.lo oht.lo htb.lo rbt.lo sll.lo gdl.lo dll.lo \
- opt.lo tio.lo tio_get.lo tio_put.lo fio.lo pio.lo sio.lo \
- alg_search.lo alg_sort.lo time.lo misc.lo assert.lo main.lo \
- stdio.lo
+ str_subst.lo str_utl.lo lda.lo oht.lo htb.lo rbt.lo sll.lo \
+ gdl.lo dll.lo opt.lo tio.lo tio_get.lo tio_put.lo fio.lo \
+ pio.lo sio.lo alg_search.lo alg_sort.lo time.lo misc.lo \
+ assert.lo main.lo stdio.lo
libqsecmn_la_OBJECTS = $(am_libqsecmn_la_OBJECTS)
libqsecmn_la_LINK = $(LIBTOOL) --tag=CC $(AM_LIBTOOLFLAGS) \
$(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \
@@ -267,7 +267,7 @@ libqsecmn_la_SOURCES = \
syscall.h mem.h \
mem.c xma.c fma.c chr.c chr_cnv.c rex.c \
str_bas.c str_chr.c str_cnv.c str_cmp.c str_cpy.c str_dyn.c str_fcpy.c \
- str_pbrk.c str_put.c str_spn.c str_utl.c \
+ str_pbrk.c str_put.c str_spn.c str_subst.c str_utl.c \
lda.c oht.c htb.c rbt.c sll.c gdl.c dll.c opt.c \
tio.c tio_get.c tio_put.c \
fio.c pio.c sio.c \
@@ -395,6 +395,7 @@ distclean-compile:
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/str_pbrk.Plo@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/str_put.Plo@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/str_spn.Plo@am__quote@
+@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/str_subst.Plo@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/str_utl.Plo@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/time.Plo@am__quote@
@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/tio.Plo@am__quote@
diff --git a/qse/lib/cmn/str_bas.c b/qse/lib/cmn/str_bas.c
index ad2a5c2c..741cff4d 100644
--- a/qse/lib/cmn/str_bas.c
+++ b/qse/lib/cmn/str_bas.c
@@ -1,5 +1,5 @@
/*
- * $Id: str_bas.c 416 2011-03-27 05:04:24Z hyunghwan.chung $
+ * $Id: str_bas.c 417 2011-03-27 14:32:37Z hyunghwan.chung $
*
Copyright 2006-2009 Chung, Hyung-Hwan.
This file is part of QSE.
@@ -43,68 +43,6 @@ qse_size_t qse_strbytes (const qse_char_t* str)
return (p - str) * QSE_SIZEOF(qse_char_t);
}
-qse_size_t qse_strxsubst (
- qse_char_t* buf, qse_size_t bsz, const qse_char_t* fmt,
- qse_strxsubst_subst_t subst, void* ctx)
-{
- qse_char_t* b = buf;
- qse_char_t* end = buf + bsz - 1;
- const qse_char_t* f = fmt;
-
- if (bsz <= 0) return 0;
-
- while (*f != QSE_T('\0'))
- {
- if (*f == QSE_T('\\'))
- {
- // get the escaped character and treat it normally.
- // if the escaper is the last character, treat it
- // normally also.
- if (f[1] != QSE_T('\0')) f++;
- }
- else if (*f == QSE_T('$'))
- {
- if (f[1] == QSE_T('{'))
- {
- const qse_char_t* tmp;
- qse_cstr_t ident;
-
- f += 2; /* skip ${ */
- tmp = f; /* mark the beginning */
-
- /* scan an enclosed segment */
- while (*f != QSE_T('\0') && *f != QSE_T('}')) f++;
-
- if (*f != QSE_T('}'))
- {
- /* restore to the position of $ */
- f = tmp - 2;
- goto normal;
- }
-
- f++; /* skip } */
-
- ident.ptr = tmp;
- ident.len = f - tmp - 1;
-
- b = subst (b, end - b, &ident, ctx);
- if (b >= end) goto fini;
-
- continue;
- }
- else if (f[1] == QSE_T('$')) f++;
- }
-
- normal:
- if (b >= end) break;
- *b++ = *f++;
- }
-
-fini:
- *b = QSE_T('\0');
- return b - buf;
-}
-
qse_size_t qse_strxcat (qse_char_t* buf, qse_size_t bsz, const qse_char_t* str)
{
qse_char_t* p, * p2;
diff --git a/qse/lib/cmn/str_subst.c b/qse/lib/cmn/str_subst.c
new file mode 100644
index 00000000..36d5f643
--- /dev/null
+++ b/qse/lib/cmn/str_subst.c
@@ -0,0 +1,145 @@
+/*
+ * $Id$
+ *
+ Copyright 2006-2009 Chung, Hyung-Hwan.
+ This file is part of QSE.
+
+ QSE is free software: you can redistribute it and/or modify
+ it under the terms of the GNU Lesser General Public License as
+ published by the Free Software Foundation, either version 3 of
+ the License, or (at your option) any later version.
+
+ QSE is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with QSE. If not, see .
+ */
+
+#include
+
+qse_size_t qse_mbsxsubst (
+ qse_mchar_t* buf, qse_size_t bsz, const qse_mchar_t* fmt,
+ qse_mbsxsubst_subst_t subst, void* ctx)
+{
+ qse_mchar_t* b = buf;
+ qse_mchar_t* end = buf + bsz - 1;
+ const qse_mchar_t* f = fmt;
+
+ if (bsz <= 0) return 0;
+
+ while (*f != QSE_MT('\0'))
+ {
+ if (*f == QSE_MT('\\'))
+ {
+ // get the escaped character and treat it normally.
+ // if the escaper is the last character, treat it
+ // normally also.
+ if (f[1] != QSE_MT('\0')) f++;
+ }
+ else if (*f == QSE_MT('$'))
+ {
+ if (f[1] == QSE_MT('{'))
+ {
+ const qse_mchar_t* tmp;
+ qse_mcstr_t ident;
+
+ f += 2; /* skip ${ */
+ tmp = f; /* mark the beginning */
+
+ /* scan an enclosed segment */
+ while (*f != QSE_MT('\0') && *f != QSE_MT('}')) f++;
+
+ if (*f != QSE_MT('}'))
+ {
+ /* restore to the position of $ */
+ f = tmp - 2;
+ goto normal;
+ }
+
+ f++; /* skip } */
+
+ ident.ptr = tmp;
+ ident.len = f - tmp - 1;
+
+ b = subst (b, end - b, &ident, ctx);
+ if (b >= end) goto fini;
+
+ continue;
+ }
+ else if (f[1] == QSE_MT('$')) f++;
+ }
+
+ normal:
+ if (b >= end) break;
+ *b++ = *f++;
+ }
+
+fini:
+ *b = QSE_MT('\0');
+ return b - buf;
+}
+
+qse_size_t qse_wcsxsubst (
+ qse_wchar_t* buf, qse_size_t bsz, const qse_wchar_t* fmt,
+ qse_wcsxsubst_subst_t subst, void* ctx)
+{
+ qse_wchar_t* b = buf;
+ qse_wchar_t* end = buf + bsz - 1;
+ const qse_wchar_t* f = fmt;
+
+ if (bsz <= 0) return 0;
+
+ while (*f != QSE_WT('\0'))
+ {
+ if (*f == QSE_WT('\\'))
+ {
+ // get the escaped character and treat it normally.
+ // if the escaper is the last character, treat it
+ // normally also.
+ if (f[1] != QSE_WT('\0')) f++;
+ }
+ else if (*f == QSE_WT('$'))
+ {
+ if (f[1] == QSE_WT('{'))
+ {
+ const qse_wchar_t* tmp;
+ qse_wcstr_t ident;
+
+ f += 2; /* skip ${ */
+ tmp = f; /* mark the beginning */
+
+ /* scan an enclosed segment */
+ while (*f != QSE_WT('\0') && *f != QSE_WT('}')) f++;
+
+ if (*f != QSE_WT('}'))
+ {
+ /* restore to the position of $ */
+ f = tmp - 2;
+ goto normal;
+ }
+
+ f++; /* skip } */
+
+ ident.ptr = tmp;
+ ident.len = f - tmp - 1;
+
+ b = subst (b, end - b, &ident, ctx);
+ if (b >= end) goto fini;
+
+ continue;
+ }
+ else if (f[1] == QSE_WT('$')) f++;
+ }
+
+ normal:
+ if (b >= end) break;
+ *b++ = *f++;
+ }
+
+fini:
+ *b = QSE_WT('\0');
+ return b - buf;
+}