[uim-commit] r1895 - branches/r5rs/sigscheme

yamaken at freedesktop.org yamaken at freedesktop.org
Sun Oct 30 01:33:57 PDT 2005


Author: yamaken
Date: 2005-10-30 01:33:51 -0700 (Sun, 30 Oct 2005)
New Revision: 1895

Added:
   branches/r5rs/sigscheme/strport.c
   branches/r5rs/sigscheme/strport.h
Modified:
   branches/r5rs/sigscheme/config.h
Log:
* This commit implements string port as ScmBytePort

* sigscheme/strport.h
  - New file
  - (ScmInputStrPort_vptr, ScmOutputStrPort_vptr): New variable decl
  - (Scm_strport_init, ScmInputStrPort_new,
    ScmInputStrPort_new_copying, ScmInputStrPort_ref_opaque,
    ScmOutputStrPort_new, ScmOutputStrPort_str,
    ScmOutputStrPort_ref_opaque): New function decl
* sigscheme/strport.c
  - New file
  - (struct ScmInputStrPort_, ScmInputStrPort, struct
    ScmOutputStrPort_, ScmOutputStrPort): New type
  - (ScmInputStrPort_vtbl, ScmOutputStrPort_vtbl): New static variable
  - (ScmInputStrPort_vptr, ScmOutputStrPort_vptr): New variable
  - (istrport_dyn_cast, istrport_close, istrport_get_byte,
    istrport_peek_byte, istrport_byte_readyp, istrport_vprintf,
    istrport_puts, istrport_write, istrport_flush, ostrport_dyn_cast,
    ostrport_close, ostrport_get_byte, ostrport_peek_byte,
    ostrport_byte_readyp, ostrport_vprintf, ostrport_puts,
    ostrport_write, ostrport_flush, ostrport_append): New static function
  - (Scm_strport_init, ScmInputStrPort_new,
    ScmInputStrPort_new_copying, ScmInputStrPort_ref_opaque,
    ScmOutputStrPort_new, ScmOutputStrPort_str,
    ScmOutputStrPort_ref_opaque): New function
* sigscheme/config.h
  - (HAVE_VASPRINTF): New macro


Modified: branches/r5rs/sigscheme/config.h
===================================================================
--- branches/r5rs/sigscheme/config.h	2005-10-30 08:24:33 UTC (rev 1894)
+++ branches/r5rs/sigscheme/config.h	2005-10-30 08:33:51 UTC (rev 1895)
@@ -96,6 +96,15 @@
 #define SCM_DEBUG_BACKTRACE_VAL 1  /* enable values printing on backtrace */
 
 /*===========================================================================
+  Platform Dependency
+===========================================================================*/
+/*
+ * FIXME: detect with configure and link against a replace function if not
+ * found
+ */
+#define HAVE_VASPRINTF          1
+
+/*===========================================================================
   Dependency Resolution
 ===========================================================================*/
 #if SCM_COMPAT_SIOD

Added: branches/r5rs/sigscheme/strport.c
===================================================================
--- branches/r5rs/sigscheme/strport.c	2005-10-30 08:24:33 UTC (rev 1894)
+++ branches/r5rs/sigscheme/strport.c	2005-10-30 08:33:51 UTC (rev 1895)
@@ -0,0 +1,396 @@
+/*===========================================================================
+ *  FileName : strport.c
+ *  About    : A ScmBytePort implementation for string
+ *
+ *  Copyright (C) 2005      by YamaKen (yamaken AT bp.iij4u.or.jp)
+ *
+ *  All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions
+ *  are met:
+ *
+ *  1. Redistributions of source code must retain the above copyright
+ *     notice, this list of conditions and the following disclaimer.
+ *  2. Redistributions in binary form must reproduce the above copyright
+ *     notice, this list of conditions and the following disclaimer in the
+ *     documentation and/or other materials provided with the distribution.
+ *  3. Neither the name of authors nor the names of its contributors
+ *     may be used to endorse or promote products derived from this software
+ *     without specific prior written permission.
+ *
+ *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS
+ *  IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ *  THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ *  PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR
+ *  CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ *  EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ *  PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ *  OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ *  WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ *  OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ *  ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+===========================================================================*/
+
+/*
+ * - This file is intended to be portable. Don't depend on SigScheme.
+ * - To isolate and hide implementation-dependent things, don't merge this file
+ *   into another
+ */
+
+/*=======================================
+  System Include
+=======================================*/
+#include <stdlib.h>
+#include <stdio.h>
+#include <stdarg.h>
+#include <string.h>
+
+/*=======================================
+  Local Include
+=======================================*/
+#include "baseport.h"
+#include "strport.h"
+
+/*=======================================
+  File Local Macro Definitions
+=======================================*/
+#define OK 0
+
+/*=======================================
+  File Local Type Definitions
+=======================================*/
+typedef struct ScmInputStrPort_  ScmInputStrPort;
+typedef struct ScmOutputStrPort_ ScmOutputStrPort;
+
+/* inherits ScmBytePort */
+struct ScmInputStrPort_ {
+    const ScmBytePortVTbl *vptr;
+
+    char *str;
+    const char *cur;
+    int has_str_ownership;
+    void *opaque;  /* client-specific opaque information */
+};
+
+/* inherits ScmBytePort */
+struct ScmOutputStrPort_ {
+    const ScmBytePortVTbl *vptr;
+
+    char *str;
+    size_t cur;       /* offset to terminal '\0' */
+    size_t buf_size;
+    void *opaque;     /* client-specific opaque information */
+};
+
+/*=======================================
+  File Local Function Declarations
+=======================================*/
+static ScmBytePort *istrport_dyn_cast(ScmBytePort *bport,
+                                      const ScmBytePortVTbl *dest_vptr);
+static int istrport_close(ScmInputStrPort *port);
+static int istrport_get_byte(ScmInputStrPort *port);
+static int istrport_peek_byte(ScmInputStrPort *port);
+static int istrport_byte_readyp(ScmInputStrPort *port);
+static int istrport_vprintf(ScmInputStrPort *port,
+                            const char *str, va_list args);
+static int istrport_puts(ScmInputStrPort *port, const char *str);
+static size_t istrport_write(ScmInputStrPort *port,
+                             size_t nbytes, const char *buf);
+static int istrport_flush(ScmInputStrPort *port);
+
+static ScmBytePort *ostrport_dyn_cast(ScmBytePort *bport,
+                                      const ScmBytePortVTbl *dest_vptr);
+static int ostrport_close(ScmOutputStrPort *port);
+static int ostrport_get_byte(ScmOutputStrPort *port);
+static int ostrport_peek_byte(ScmOutputStrPort *port);
+static int ostrport_byte_readyp(ScmOutputStrPort *port);
+static int ostrport_vprintf(ScmOutputStrPort *port,
+                            const char *str, va_list args);
+static int ostrport_puts(ScmOutputStrPort *port, const char *str);
+static size_t ostrport_write(ScmOutputStrPort *port,
+                             size_t nbytes, const char *buf);
+static int ostrport_flush(ScmOutputStrPort *port);
+
+static size_t ostrport_append(ScmOutputStrPort *port,
+                              size_t len, const char *str);
+
+/*=======================================
+  Variable Declarations
+=======================================*/
+static const ScmBytePortVTbl ScmInputStrPort_vtbl = {
+    (ScmBytePortMethod_dyn_cast)   &istrport_dyn_cast,
+    (ScmBytePortMethod_close)      &istrport_close,
+    (ScmBytePortMethod_get_byte)   &istrport_get_byte,
+    (ScmBytePortMethod_peek_byte)  &istrport_peek_byte,
+    (ScmBytePortMethod_byte_readyp)&istrport_byte_readyp,
+    (ScmBytePortMethod_vprintf)    &istrport_vprintf,
+    (ScmBytePortMethod_puts)       &istrport_puts,
+    (ScmBytePortMethod_write)      &istrport_write,
+    (ScmBytePortMethod_flush)      &istrport_flush
+};
+const ScmBytePortVTbl *ScmInputStrPort_vptr = &ScmInputStrPort_vtbl;
+
+static const ScmBytePortVTbl ScmOutputStrPort_vtbl = {
+    (ScmBytePortMethod_dyn_cast)   &ostrport_dyn_cast,
+    (ScmBytePortMethod_close)      &ostrport_close,
+    (ScmBytePortMethod_get_byte)   &ostrport_get_byte,
+    (ScmBytePortMethod_peek_byte)  &ostrport_peek_byte,
+    (ScmBytePortMethod_byte_readyp)&ostrport_byte_readyp,
+    (ScmBytePortMethod_vprintf)    &ostrport_vprintf,
+    (ScmBytePortMethod_puts)       &ostrport_puts,
+    (ScmBytePortMethod_write)      &ostrport_write,
+    (ScmBytePortMethod_flush)      &ostrport_flush
+};
+const ScmBytePortVTbl *ScmOutputStrPort_vptr = &ScmOutputStrPort_vtbl;
+
+/*=======================================
+  Function Implementations
+=======================================*/
+
+/*
+ * Client code must call this first even if current implementation does not
+ * contain actual code.
+ */
+void Scm_strport_init(void)
+{
+    return;
+}
+
+ScmBytePort *
+ScmInputStrPort_new(char *str, int ownership)
+{
+    ScmInputStrPort *port;
+
+    port = malloc(sizeof(ScmInputStrPort));
+    if (!port)
+        SCM_BYTEPORT_ERROR_NOMEM(NULL, ScmInputStrPort);
+
+    port->vptr = ScmInputStrPort_vptr;
+    port->cur = port->str = str;
+    port->has_str_ownership = ownership;
+    port->opaque = NULL;
+
+    return (ScmBytePort *)port;
+}
+
+ScmBytePort *
+ScmInputStrPort_new_copying(char *str)
+{
+    return ScmInputStrPort_new(strdup(str), TRUE);
+}
+
+void **
+ScmInputStrPort_ref_opaque(ScmBytePort *bport)
+{
+    ScmInputStrPort *port;
+
+    port = SCM_PORT_DYNAMIC_CAST(ScmInputStrPort, bport);
+    if (!port)
+        SCM_BYTEPORT_ERROR_INVALID_TYPE(bport, ScmInputStrPort);
+
+    return &port->opaque;
+}
+
+static ScmBytePort *
+istrport_dyn_cast(ScmBytePort *bport, const ScmBytePortVTbl *dst_vptr)
+{
+    if (dst_vptr != ScmInputStrPort_vptr)
+        SCM_BYTEPORT_ERROR_INVALID_TYPE(bport, ScmInputStrPort);
+
+    return bport;
+}
+
+static int
+istrport_close(ScmInputStrPort *port)
+{
+    if (port->has_str_ownership)
+        free(port->str);
+    free(port);
+
+    return OK;
+}
+
+static int
+istrport_get_byte(ScmInputStrPort *port)
+{
+    return (*port->cur) ? *port->cur++ : EOF;
+}
+
+static int
+istrport_peek_byte(ScmInputStrPort *port)
+{
+    return (*port->cur) ? *port->cur : EOF;
+}
+
+static int
+istrport_byte_readyp(ScmInputStrPort *port)
+{
+    return TRUE;
+}
+
+static int
+istrport_vprintf(ScmInputStrPort *port, const char *str, va_list args)
+{
+    SCM_BYTEPORT_ERROR_INVALID_OPERATION(port, ScmInputStrPort);
+}
+
+static int
+istrport_puts(ScmInputStrPort *port, const char *str)
+{
+    SCM_BYTEPORT_ERROR_INVALID_OPERATION(port, ScmInputStrPort);
+}
+
+static size_t
+istrport_write(ScmInputStrPort *port, size_t nbytes, const char *buf)
+{
+    SCM_BYTEPORT_ERROR_INVALID_OPERATION(port, ScmInputStrPort);
+}
+
+static int
+istrport_flush(ScmInputStrPort *port)
+{
+    SCM_BYTEPORT_ERROR_INVALID_OPERATION(port, ScmInputStrPort);
+}
+
+
+ScmBytePort *
+ScmOutputStrPort_new(void)
+{
+    ScmOutputStrPort *port;
+
+    port = malloc(sizeof(ScmOutputStrPort));
+    if (!port)
+        SCM_BYTEPORT_ERROR_NOMEM(NULL, ScmOutputStrPort);
+
+    port->vptr = ScmOutputStrPort_vptr;
+    port->str = NULL;
+    port->cur = 0;
+    port->buf_size = 0;
+    port->opaque = NULL;
+
+    return (ScmBytePort *)port;
+}
+
+/* may return NULL */
+const char *
+ScmOutputStrPort_str(ScmBytePort *bport)
+{
+    ScmOutputStrPort *port;
+
+    port = SCM_PORT_DYNAMIC_CAST(ScmOutputStrPort, bport);
+    if (!port)
+        SCM_BYTEPORT_ERROR_INVALID_TYPE(bport, ScmOutputStrPort);
+
+    return port->str;
+}
+
+void **
+ScmOutputStrPort_ref_opaque(ScmBytePort *bport)
+{
+    ScmOutputStrPort *port;
+
+    port = SCM_PORT_DYNAMIC_CAST(ScmOutputStrPort, bport);
+    if (!port)
+        SCM_BYTEPORT_ERROR_INVALID_TYPE(bport, ScmOutputStrPort);
+
+    return &port->opaque;
+}
+
+static ScmBytePort *
+ostrport_dyn_cast(ScmBytePort *bport, const ScmBytePortVTbl *dst_vptr)
+{
+    if (dst_vptr != ScmOutputStrPort_vptr)
+        SCM_BYTEPORT_ERROR_INVALID_TYPE(bport, ScmOutputStrPort);
+
+    return bport;
+}
+
+static int
+ostrport_close(ScmOutputStrPort *port)
+{
+    free(port->str);
+    free(port);
+
+    return OK;
+}
+
+static int
+ostrport_get_byte(ScmOutputStrPort *port)
+{
+    SCM_BYTEPORT_ERROR_INVALID_OPERATION(port, ScmOutputStrPort);
+}
+
+static int
+ostrport_peek_byte(ScmOutputStrPort *port)
+{
+    SCM_BYTEPORT_ERROR_INVALID_OPERATION(port, ScmOutputStrPort);
+}
+
+static int
+ostrport_byte_readyp(ScmOutputStrPort *port)
+{
+    SCM_BYTEPORT_ERROR_INVALID_OPERATION(port, ScmOutputStrPort);
+}
+
+static int
+ostrport_vprintf(ScmOutputStrPort *port, const char *str, va_list args)
+{
+#if HAVE_VASPRINTF
+    char *appendix;
+    int len;
+    
+    len = vasprintf(&appendix, str, args);
+    if (!appendix)
+        SCM_BYTEPORT_ERROR_NOMEM(port, ScmOutputStrPort);
+    if (0 < len)
+        ostrport_append(port, len, appendix);
+    free(appendix);
+
+    return len;
+#else
+    /* FIXME */
+#error "This platform is not supported yet"
+#endif
+}
+
+static int
+ostrport_puts(ScmOutputStrPort *port, const char *str)
+{
+    ostrport_append(port, strlen(str), str);
+
+    return OK;
+}
+
+static size_t
+ostrport_write(ScmOutputStrPort *port, size_t nbytes, const char *buf)
+{
+    return ostrport_append(port, nbytes, buf);
+}
+
+static int
+ostrport_flush(ScmOutputStrPort *port)
+{
+    return OK;
+}
+
+static size_t
+ostrport_append(ScmOutputStrPort *port, size_t len, const char *str)
+{
+    char *new_str;
+
+    /* extend the buffer */
+    if (port->buf_size - port->cur < len + sizeof((char)'\0')) {
+        port->buf_size += len;
+        new_str = realloc(port->str, port->buf_size);
+        if (!new_str)
+            SCM_BYTEPORT_ERROR_NOMEM(NULL, ScmOutputStrPort);
+        port->str = new_str;
+    }
+
+    memcpy(port->str + port->cur, str, len);
+    port->cur += len;
+    new_str[port->cur] = '\0';
+
+    return len + sizeof((char)'\0');
+}

Added: branches/r5rs/sigscheme/strport.h
===================================================================
--- branches/r5rs/sigscheme/strport.h	2005-10-30 08:24:33 UTC (rev 1894)
+++ branches/r5rs/sigscheme/strport.h	2005-10-30 08:33:51 UTC (rev 1895)
@@ -0,0 +1,80 @@
+/*===========================================================================
+ *  FileName : strport.h
+ *  About    : A ScmBytePort implementation for string
+ *
+ *  Copyright (C) 2005      by YamaKen (yamaken AT bp.iij4u.or.jp)
+ *
+ *  All rights reserved.
+ *
+ *  Redistribution and use in source and binary forms, with or without
+ *  modification, are permitted provided that the following conditions
+ *  are met:
+ *
+ *  1. Redistributions of source code must retain the above copyright
+ *     notice, this list of conditions and the following disclaimer.
+ *  2. Redistributions in binary form must reproduce the above copyright
+ *     notice, this list of conditions and the following disclaimer in the
+ *     documentation and/or other materials provided with the distribution.
+ *  3. Neither the name of authors nor the names of its contributors
+ *     may be used to endorse or promote products derived from this software
+ *     without specific prior written permission.
+ *
+ *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS
+ *  IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ *  THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ *  PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR
+ *  CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ *  EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ *  PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ *  OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ *  WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ *  OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ *  ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+===========================================================================*/
+
+/*
+ * This file is intended to be portable. Don't depend on SigScheme and don't
+ * merge into another file.
+ */
+
+#ifndef __SCM_STRPORT_H
+#define __SCM_STRPORT_H
+
+/*=======================================
+  System Include
+=======================================*/
+
+/*=======================================
+  Local Include
+=======================================*/
+#include "baseport.h"
+
+/*=======================================
+  Macro Definitions
+=======================================*/
+
+/*=======================================
+  Type Definitions
+=======================================*/
+
+/*=======================================
+   Variable Declarations
+=======================================*/
+extern const ScmBytePortVTbl *ScmInputStrPort_vptr;
+extern const ScmBytePortVTbl *ScmOutputStrPort_vptr;
+
+/*=======================================
+   Function Declarations
+=======================================*/
+void Scm_strport_init(void);
+
+ScmBytePort *ScmInputStrPort_new(char *str, int ownership);
+ScmBytePort *ScmInputStrPort_new_copying(char *str);
+void **ScmInputStrPort_ref_opaque(ScmBytePort *bport);
+
+ScmBytePort *ScmOutputStrPort_new(void);
+const char *ScmOutputStrPort_str(ScmBytePort *bport);
+void **ScmOutputStrPort_ref_opaque(ScmBytePort *bport);
+
+
+#endif /* __SCM_STRPORT_H */



More information about the uim-commit mailing list