Synesis Software STLSoft - ... Robust, Lightweight, Cross-platform, Template Software ...

fastformat/sinks/c_string.hpp

Go to the documentation of this file.
00001 /* /////////////////////////////////////////////////////////////////////////
00002  * File:        fastformat/sinks/c_string.hpp
00003  *
00004  * Purpose:     A FastFormat sink for fixed length character buffers to be
00005  *              filled as C-style strings.
00006  *
00007  * Created:     14th April 2008
00008  * Updated:     30th April 2010
00009  *
00010  * Home:        http://www.fastformat.org/
00011  *
00012  * Copyright (c) 2008-2010, Matthew Wilson and Synesis Software
00013  * All rights reserved.
00014  *
00015  * Redistribution and use in source and binary forms, with or without
00016  * modification, are permitted provided that the following conditions are
00017  * met:
00018  *
00019  * - Redistributions of source code must retain the above copyright notice,
00020  *   this list of conditions and the following disclaimer.
00021  * - Redistributions in binary form must reproduce the above copyright
00022  *   notice, this list of conditions and the following disclaimer in the
00023  *   documentation and/or other materials provided with the distribution.
00024  * - Neither the names of Matthew Wilson and Synesis Software nor the names
00025  *   of any contributors may be used to endorse or promote products derived
00026  *   from this software without specific prior written permission.
00027  *
00028  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
00029  * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
00030  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
00031  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
00032  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
00033  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
00034  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
00035  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
00036  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00037  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
00038  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00039  *
00040  * ////////////////////////////////////////////////////////////////////// */
00041 
00042 
00049 #ifndef FASTFORMAT_INCL_FASTFORMAT_SINK_HPP_C_STRING
00050 #define FASTFORMAT_INCL_FASTFORMAT_SINK_HPP_C_STRING
00051 
00052 /* /////////////////////////////////////////////////////////////////////////
00053  * Version information
00054  */
00055 
00056 #ifndef FASTFORMAT_DOCUMENTATION_SKIP_SECTION
00057 # define FASTFORMAT_VER_FASTFORMAT_SINK_HPP_C_STRING_MAJOR      1
00058 # define FASTFORMAT_VER_FASTFORMAT_SINK_HPP_C_STRING_MINOR      2
00059 # define FASTFORMAT_VER_FASTFORMAT_SINK_HPP_C_STRING_REVISION   1
00060 # define FASTFORMAT_VER_FASTFORMAT_SINK_HPP_C_STRING_EDIT       12
00061 #endif /* !FASTFORMAT_DOCUMENTATION_SKIP_SECTION */
00062 
00063 /* /////////////////////////////////////////////////////////////////////////
00064  * Language
00065  */
00066 
00067 #ifndef __cplusplus
00068 # error This file can only be included in C++ compilation units
00069 #endif /* !__cplusplus */
00070 
00071 /* /////////////////////////////////////////////////////////////////////////
00072  * Includes
00073  */
00074 
00075 #include <fastformat/fastformat.h>
00076 #include <fastformat/quality/contract.h>
00077 #include <fastformat/util/sinks/helpers.hpp>
00078 #include <fastformat/format/standard_flags.hpp>
00079 
00080 #include <stdexcept>
00081 
00082 /* /////////////////////////////////////////////////////////////////////////
00083  * Namespace
00084  */
00085 
00086 #if !defined(FASTFORMAT_NO_NAMESPACE)
00087 namespace fastformat
00088 {
00089 namespace sinks
00090 {
00091 #endif /* !FASTFORMAT_NO_NAMESPACE */
00092 
00093 /* /////////////////////////////////////////////////////////////////////////
00094  * Classes
00095  */
00096 
00099 class c_string_sink
00100 {
00101 public:
00103     typedef c_string_sink       class_type;
00105     typedef ff_char_t           char_type;
00107     typedef size_t              size_type;
00108 
00109 public:
00111     c_string_sink(size_type n, char_type* buffer)
00112         : m_capacity(n)
00113         , m_len(0)
00114         , m_buffer(buffer)
00115     {}
00116 #ifdef STLSOFT_CF_STATIC_ARRAY_SIZE_DETERMINATION_SUPPORT
00118     template <size_t N>
00119     c_string_sink(char_type (&ar)[N])
00120         : m_capacity(N)
00121         , m_len(0)
00122         , m_buffer(&ar[0])
00123     {}
00124 #endif /* STLSOFT_CF_STATIC_ARRAY_SIZE_DETERMINATION_SUPPORT */
00125 
00126 public: // Attributes
00128     size_type size() const
00129     {
00130         return m_len;
00131     }
00133     size_type capacity() const
00134     {
00135         return m_capacity;
00136     }
00137 
00138 public: // Operations
00140     class_type& write(size_type cchTotal, size_type numResults, ff_string_slice_t const* results, int flags)
00141     {
00142         const ff_string_slice_t crlf            =   fastformat_getNewlineForPlatform();
00143 
00144         const size_type         requiredSize    =   size()
00145                                                     +   cchTotal
00146                                                     +   ((flags::ff_newLine & flags) ? crlf.len : 0)
00147                                                     +   1
00148                                                     ;
00149 
00150         if(requiredSize > capacity())
00151         {
00152             throw std::out_of_range("character buffer sink capacity exceeded");
00153         }
00154         else
00155         {
00156             char_type* p = &m_buffer[0] + size();
00157 
00158             // next we concatenate all the slices
00159 
00160             { for(size_type i = 0; i < numResults; ++i)
00161             {
00162                 ff_string_slice_t const& slice = results[i];
00163 
00164                 ::memcpy(p, slice.ptr, slice.len * sizeof(char_type));
00165                 p += slice.len;
00166             }}
00167 
00168             // then append the new line, if required
00169 
00170             if(flags::ff_newLine & flags)
00171             {
00172                 const ff_string_slice_t crlf = fastformat_getNewlineForPlatform();
00173 
00174                 ::memcpy(p, crlf.ptr, crlf.len * sizeof(char_type));
00175                 p += crlf.len;
00176             }
00177 
00178             *p++ = '\0';
00179 
00180             m_len += cchTotal;
00181 
00182             FASTFORMAT_CONTRACT_ENFORCE_POSTCONDITION_STATE_APPL_LAYER(p == &m_buffer[0] + size() + 1, "c_string sink writing logic failed: write pointer in wrong place");
00183         }
00184 
00185         return *this;
00186     }
00187 
00188 private: // Member variables
00189     const size_type     m_capacity;
00190     size_t              m_len;
00191     char_type* const    m_buffer;
00192 
00193 private: // Not to be implemented
00194     c_string_sink(class_type const&);
00195     class_type& operator =(class_type const&);
00196 };
00197 
00198 /* /////////////////////////////////////////////////////////////////////////
00199  * Action Shims
00200  */
00201 
00205 inline c_string_sink& fmt_slices(c_string_sink& sink, int flags, size_t cchTotal, size_t numResults, ff_string_slice_t const* results)
00206 {
00207     return sink.write(cchTotal, numResults, results, flags);
00208 }
00209 
00210 /* /////////////////////////////////////////////////////////////////////////
00211  * Namespace
00212  */
00213 
00214 #if !defined(FASTFORMAT_NO_NAMESPACE)
00215 } /* namespace sinks */
00216 } /* namespace fastformat */
00217 #endif /* !FASTFORMAT_NO_NAMESPACE */
00218 
00219 /* ////////////////////////////////////////////////////////////////////// */
00220 
00221 #endif /* FASTFORMAT_INCL_FASTFORMAT_SINK_HPP_C_STRING */
00222 
00223 /* ///////////////////////////// end of file //////////////////////////// */

FastFormat Library documentation © Matthew Wilson, 2006-2009 SourceForge.net Logo