You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@commons.apache.org by mt...@apache.org on 2009/12/12 08:54:17 UTC
svn commit: r889894 - in /commons/sandbox/runtime/trunk/src/main/native:
include/acr_sbuf.h shared/sbuf.c
Author: mturk
Date: Sat Dec 12 07:54:15 2009
New Revision: 889894
URL: http://svn.apache.org/viewvc?rev=889894&view=rev
Log:
Add wide version of sbuf
Modified:
commons/sandbox/runtime/trunk/src/main/native/include/acr_sbuf.h
commons/sandbox/runtime/trunk/src/main/native/shared/sbuf.c
Modified: commons/sandbox/runtime/trunk/src/main/native/include/acr_sbuf.h
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/include/acr_sbuf.h?rev=889894&r1=889893&r2=889894&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/include/acr_sbuf.h (original)
+++ commons/sandbox/runtime/trunk/src/main/native/include/acr_sbuf.h Sat Dec 12 07:54:15 2009
@@ -72,6 +72,15 @@
int s_flags; /* flags */
};
+typedef struct acr_wbuf_t acr_wbuf_t;
+
+struct acr_wbuf_t {
+ wchar_t *s_buf; /* storage buffer */
+ size_t s_size; /* size of storage buffer */
+ size_t s_len; /* current length of string */
+ int s_flags; /* flags */
+};
+
/**
* Sbuf API functions
*/
@@ -87,6 +96,7 @@
int acr_sbuf_printf(acr_sbuf_t *, const char *, ...);
int acr_sbuf_vprintf(acr_sbuf_t *, const char *, va_list);
int acr_sbuf_putc(acr_sbuf_t *, int);
+int acr_sbuf_putb(acr_sbuf_t *, int);
int acr_sbuf_rtrim(acr_sbuf_t *);
char *acr_sbuf_ltrim(acr_sbuf_t *);
char *acr_sbuf_trim(acr_sbuf_t *);
@@ -97,6 +107,27 @@
int acr_sbuf_done(acr_sbuf_t *);
void acr_sbuf_delete(acr_sbuf_t *);
+acr_wbuf_t *acr_wbuf_new(acr_wbuf_t *, wchar_t *, size_t, int);
+#define acr_wbuf_new_auto() \
+ acr_wbuf_new(NULL, NULL, 0, ACR_SBUF_AUTOEXTEND)
+void acr_wbuf_clear(acr_wbuf_t *);
+int acr_wbuf_setpos(acr_wbuf_t *, size_t);
+int acr_wbuf_bcat(acr_wbuf_t *, const void *, size_t);
+int acr_wbuf_bcpy(acr_wbuf_t *, const void *, size_t);
+int acr_wbuf_cat(acr_wbuf_t *, const wchar_t *);
+int acr_wbuf_cpy(acr_wbuf_t *, const wchar_t *);
+int acr_wbuf_putc(acr_wbuf_t *, int);
+int acr_wbuf_putb(acr_wbuf_t *, int);
+int acr_wbuf_rtrim(acr_wbuf_t *);
+wchar_t *acr_wbuf_ltrim(acr_wbuf_t *);
+wchar_t *acr_wbuf_trim(acr_wbuf_t *);
+int acr_wbuf_overflowed(acr_wbuf_t *);
+void acr_wbuf_finish(acr_wbuf_t *);
+wchar_t *acr_wbuf_data(acr_wbuf_t *);
+size_t acr_wbuf_len(acr_wbuf_t *);
+int acr_wbuf_done(acr_wbuf_t *);
+void acr_wbuf_delete(acr_wbuf_t *);
+
#ifdef __cplusplus
}
#endif
Modified: commons/sandbox/runtime/trunk/src/main/native/shared/sbuf.c
URL: http://svn.apache.org/viewvc/commons/sandbox/runtime/trunk/src/main/native/shared/sbuf.c?rev=889894&r1=889893&r2=889894&view=diff
==============================================================================
--- commons/sandbox/runtime/trunk/src/main/native/shared/sbuf.c (original)
+++ commons/sandbox/runtime/trunk/src/main/native/shared/sbuf.c Sat Dec 12 07:54:15 2009
@@ -344,6 +344,23 @@
}
/*
+ * Append a character to an sbuf allowing NUL.
+ */
+int
+acr_sbuf_putb(acr_sbuf_t *s, int c)
+{
+
+ if (SBUF_HASOVERFLOWED(s))
+ return -1;
+ if (!SBUF_HASROOM(s) && acr_sbuf_extend(s, 1) < 0) {
+ SBUF_SETFLAG(s, ACR_SBUF_OVERFLOWED);
+ return -1;
+ }
+ s->s_buf[s->s_len++] = (char)(c & 0xFF);
+ return 0;
+}
+
+/*
* Trim whitespace characters from end of an sbuf.
*/
int
@@ -470,3 +487,345 @@
{
return SBUF_ISFINISHED(s);
}
+
+/* Wide char version of sbuf
+ */
+
+/*
+ * Extend an sbuf.
+ */
+static int
+acr_wbuf_extend(acr_wbuf_t *s, size_t addlen)
+{
+ wchar_t *newbuf;
+ size_t newsize;
+
+ if (!SBUF_CANEXTEND(s))
+ return -1;
+
+ newsize = acr_sbuf_extendsize(s->s_size + addlen);
+ newbuf = x_malloc(newsize * sizeof(wchar_t));
+ if (newbuf == NULL)
+ return -1;
+ memcpy(newbuf, s->s_buf, s->s_size * sizeof(wchar_t));
+ if (SBUF_ISDYNAMIC(s))
+ x_free(s->s_buf);
+ else
+ SBUF_SETFLAG(s, ACR_SBUF_DYNAMIC);
+ s->s_buf = newbuf;
+ s->s_size = newsize;
+
+ return 0;
+}
+
+/*
+ * Initialize an sbuf.
+ * If buf is non-NULL, it points to a static or already-allocated string
+ * big enough to hold at least length characters.
+ */
+acr_wbuf_t *
+acr_wbuf_new(acr_wbuf_t *s, wchar_t *buf, size_t length, int flags)
+{
+
+ if ((flags & ~ACR_SBUF_USRFLAGMSK)) {
+ ACR_SET_OS_ERROR(ACR_EINVAL);
+ return NULL;
+ }
+ flags &= ACR_SBUF_USRFLAGMSK;
+ if (s == NULL) {
+ s = s_calloc(acr_wbuf_t, 1);
+ if (s == NULL)
+ return NULL;
+ s->s_flags = flags;
+ SBUF_SETFLAG(s, ACR_SBUF_DYNSTRUCT);
+ } else {
+ memset(s, 0, sizeof(acr_wbuf_t));
+ s->s_flags = flags;
+ }
+ s->s_size = length;
+ if (buf) {
+ s->s_buf = buf;
+ return s;
+ }
+ if (flags & ACR_SBUF_AUTOEXTEND)
+ s->s_size = acr_sbuf_extendsize(s->s_size);
+ s->s_buf = x_malloc(s->s_size * sizeof(wchar_t));
+ if (s->s_buf == NULL) {
+ if (SBUF_ISDYNSTRUCT(s))
+ x_free(s);
+ return NULL;
+ }
+ SBUF_SETFLAG(s, ACR_SBUF_DYNAMIC);
+ return s;
+}
+
+/*
+ * Clear an sbuf and reset its position.
+ */
+void
+acr_wbuf_clear(acr_wbuf_t *s)
+{
+
+ /* don't care if it's finished or not */
+
+ SBUF_CLRFLAG(s, ACR_SBUF_FINISHED);
+ SBUF_CLRFLAG(s, ACR_SBUF_OVERFLOWED);
+ s->s_len = 0;
+}
+
+/*
+ * Set the sbuf's end position to an arbitrary value.
+ * Effectively truncates the sbuf at the new position.
+ */
+int
+acr_wbuf_setpos(acr_wbuf_t *s, size_t pos)
+{
+
+ if (pos >= s->s_size) {
+ ACR_SET_OS_ERROR(ACR_EINVAL);
+ return -1;
+ }
+ if (pos > s->s_len)
+ return -1;
+ s->s_len = pos;
+ return 0;
+}
+
+/*
+ * Append a byte string to an sbuf.
+ */
+int
+acr_wbuf_bcat(acr_wbuf_t *s, const void *buf, size_t len)
+{
+ const wchar_t *str = (const wchar_t *)buf;
+
+ if (SBUF_HASOVERFLOWED(s))
+ return -1;
+ for (; len; len--) {
+ if (!SBUF_HASROOM(s) && acr_wbuf_extend(s, len) < 0)
+ break;
+ s->s_buf[s->s_len++] = *str++;
+ }
+ if (len) {
+ SBUF_SETFLAG(s, ACR_SBUF_OVERFLOWED);
+ return -1;
+ }
+ return 0;
+}
+
+/*
+ * Copy a byte string into an sbuf.
+ */
+int
+acr_wbuf_bcpy(acr_wbuf_t *s, const void *buf, size_t len)
+{
+
+ acr_wbuf_clear(s);
+ return acr_wbuf_bcat(s, buf, len);
+}
+
+/*
+ * Append a string to an sbuf.
+ */
+int
+acr_wbuf_cat(acr_wbuf_t *s, const wchar_t *str)
+{
+
+ if (SBUF_HASOVERFLOWED(s))
+ return -1;
+ if (!str || !*str) {
+ /* Nothing to do.
+ * Empty strings cannot be added.
+ * We use finish() for that
+ */
+ return 0;
+ }
+ while (*str) {
+ if (!SBUF_HASROOM(s) && acr_wbuf_extend(s, wcslen(str)) < 0)
+ break;
+ s->s_buf[s->s_len++] = *str++;
+ }
+ if (*str) {
+ SBUF_SETFLAG(s, ACR_SBUF_OVERFLOWED);
+ return -1;
+ }
+ return 0;
+}
+
+/*
+ * Copy a string into an sbuf.
+ */
+int
+acr_wbuf_cpy(acr_wbuf_t *s, const wchar_t *str)
+{
+
+ acr_wbuf_clear(s);
+ return acr_wbuf_cat(s, str);
+}
+
+/*
+ * Append a character to an sbuf.
+ */
+int
+acr_wbuf_putc(acr_wbuf_t *s, int c)
+{
+
+ if (SBUF_HASOVERFLOWED(s))
+ return -1;
+ if (c == 0) {
+ /* Nothing to add */
+ return 0;
+ }
+ if (!SBUF_HASROOM(s) && acr_wbuf_extend(s, 1) < 0) {
+ SBUF_SETFLAG(s, ACR_SBUF_OVERFLOWED);
+ return -1;
+ }
+ s->s_buf[s->s_len++] = (wchar_t)c;
+ return 0;
+}
+
+/*
+ * Append a character to an sbuf allowing NUL.
+ */
+int
+acr_wbuf_putb(acr_wbuf_t *s, int c)
+{
+
+ if (SBUF_HASOVERFLOWED(s))
+ return -1;
+ if (!SBUF_HASROOM(s) && acr_wbuf_extend(s, 1) < 0) {
+ SBUF_SETFLAG(s, ACR_SBUF_OVERFLOWED);
+ return -1;
+ }
+ s->s_buf[s->s_len++] = (wchar_t)c;
+ return 0;
+}
+
+/*
+ * Trim whitespace characters from end of an sbuf.
+ */
+int
+acr_wbuf_rtrim(acr_wbuf_t *s)
+{
+
+ if (SBUF_HASOVERFLOWED(s))
+ return -1;
+
+ while (s->s_len && iswspace(s->s_buf[s->s_len-1]))
+ --s->s_len;
+
+ return 0;
+}
+
+/*
+ * Return pointer to the first non white space character
+ * in sbuf. The acr_sbuf_finish must be called before this
+ * function
+ */
+wchar_t *
+acr_wbuf_ltrim(acr_wbuf_t *s)
+{
+
+ wchar_t *p = s->s_buf;
+
+ if (SBUF_HASOVERFLOWED(s))
+ return NULL;
+ if (!SBUF_ISFINISHED(s))
+ return p;
+ while (*p && iswspace(*p))
+ p++;
+
+ return p;
+}
+
+/*
+ * Trim the sbuf.
+ */
+wchar_t *
+acr_wbuf_trim(acr_wbuf_t *s)
+{
+
+ wchar_t *p = s->s_buf;
+
+ acr_wbuf_rtrim(s);
+ acr_wbuf_finish(s);
+
+ while (*p && iswspace(*p))
+ p++;
+
+ return p;
+}
+
+/*
+ * Check if an sbuf overflowed
+ */
+int
+acr_wbuf_overflowed(acr_wbuf_t *s)
+{
+
+ return SBUF_HASOVERFLOWED(s);
+}
+
+/*
+ * Finish off an sbuf.
+ */
+void
+acr_wbuf_finish(acr_wbuf_t *s)
+{
+
+ s->s_buf[s->s_len] = L'\0';
+
+ SBUF_CLRFLAG(s, ACR_SBUF_OVERFLOWED);
+ SBUF_SETFLAG(s, ACR_SBUF_FINISHED);
+}
+
+/*
+ * Return a pointer to the sbuf data.
+ */
+wchar_t *
+acr_wbuf_data(acr_wbuf_t *s)
+{
+
+ return s->s_buf;
+}
+
+/*
+ * Return the length of the sbuf data.
+ */
+size_t
+acr_wbuf_len(acr_wbuf_t *s)
+{
+
+ /* don't care if it's finished or not */
+ if (SBUF_HASOVERFLOWED(s))
+ return 0;
+ return s->s_len;
+}
+
+/*
+ * Clear an sbuf, free its buffer if necessary.
+ */
+void
+acr_wbuf_delete(acr_wbuf_t *s)
+{
+ int isdyn;
+
+ /* don't care if it's finished or not */
+ if (SBUF_ISDYNAMIC(s))
+ x_free(s->s_buf);
+ isdyn = SBUF_ISDYNSTRUCT(s);
+ if (isdyn)
+ x_free(s);
+ else
+ memset(s, 0, sizeof(*s));
+}
+
+/*
+ * Check if an sbuf has been finished.
+ */
+int
+acr_wbuf_done(acr_wbuf_t *s)
+{
+ return SBUF_ISFINISHED(s);
+}
+