/**************************************************************************
 *
 * rw_char.h - defines a User Defined Character type and its traits
 *
 * $Id$
 *
 ***************************************************************************
 *
 * Licensed to the Apache Software  Foundation (ASF) under one or more
 * contributor  license agreements.  See  the NOTICE  file distributed
 * with  this  work  for  additional information  regarding  copyright
 * ownership.   The ASF  licenses this  file to  you under  the Apache
 * License, Version  2.0 (the  "License"); you may  not use  this file
 * except in  compliance with the License.   You may obtain  a copy of
 * the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the  License is distributed on an  "AS IS" BASIS,
 * WITHOUT  WARRANTIES OR CONDITIONS  OF ANY  KIND, either  express or
 * implied.   See  the License  for  the  specific language  governing
 * permissions and limitations under the License.
 *
 * Copyright 2004-2006 Rogue Wave Software.
 * 
 **************************************************************************/

#ifndef RW_CHAR_INCLUDED
#define RW_CHAR_INCLUDED


// avoid dependencies on any library headers
// to prevent the pollution of the namespace(s)
#include <rw/_traits.h>
#include <testdefs.h>


struct UserChar   // user-defined character type (must be POD)
{
#if    !defined (_RWSTD_NO_LONG_DOUBLE) \
    && !defined (__SUNPRO_CC) || __SUNPRO_CC > 0x540
    long double f;    // exercise correct alignment
#else
    // cannot use long double with SunPro due to a compiler
    // bug that prevents assignments of UserChar() (PR #28328)
    double f;
#endif   // _RWSTD_NO_LONG_DOUBLE

    unsigned char c;   // underlying character representation

    static UserChar eos () {
        // use UserChar::eos() instead of UserChar() to work around broken
        // compilers (e.g., MSVC 6) that do not zero out POD structs
        // on default construction
        const UserChar tmp = { 0, 0 };
        return tmp;
    }

    // definition of a POD-struct (9, p4):
    // A POD-struct is an aggregate class that has no non-static data
    // members of type pointer to member, non-POD-struct, non-POD-union
    // (or array of such types) or reference, and has no user-defined
    // copy assign-ment operator and no user-defined destructor.

    // definition of an aggregate (8.5.1, p1):
    // An aggregate is an array or a class (clause 9) with no user-declared
    // constructors (12.1), no private or protected non-static data members
    // (clause 11), no base classes (clause 10), and no virtual functions
    // (10.3).
};


inline UserChar make_char (char c, UserChar*)
{
    const UserChar ch = { 0.0, c };
    return ch;
}

inline char make_char (char c, char*)
{
    return c;
}

#ifndef _RWSTD_NO_WCHAR_T

inline wchar_t make_char (char c, wchar_t*)
{
    typedef unsigned char UChar;
    return wchar_t (UChar (c));
}

#endif   // _RWSTD_NO_WCHAR_T

///////////////////////////////////////////////////////////////////////////
// 21.1.2, p2 of C++ 03:
//
//   typedef INT_T int_type;
//
// -2- Requires: For a certain character container type char_type, a related
//     container type INT_T shall be a type or class which can represent all
//     of the valid characters converted from the corresponding char_type
//     values, as well as an end-of-file value, eof(). The type int_type
//     represents a character container type which can hold end-of-file to
//     be used as a return type of the iostream class member functions.224)
// ____________
// Footnote 224: If eof() can be held in char_type then some iostreams
//               operations may give surprising results.

class UserInt
{
    void* ptr_;   // to check validity
    int   i_;     // underlying int representation

    // valid values are 0 through 256 with 256 representing EOF
public:

    // default ctor creates a valid object but assigns it an invalid
    // value so that the only legal operations on it are assignment
    // and copy
    UserInt (): ptr_ (&i_ /* valid */), i_ (-1 /* invalid */) { /* empty */ }

    UserInt (const UserInt &rhs)
        : ptr_ (&i_), i_ (rhs.i_) {
        // verify rhs is valid 
        // const_cast used to avoid MSVC 7.0 error C2446:
        // '==' : no conversion from 'const int *' to 'void *const '
        RW_ASSERT (_RWSTD_CONST_CAST (const void*, rhs.ptr_) == &rhs.i_);
        RW_ASSERT (-1 <= rhs.i_  && rhs.i_ < 257);   // i may be invalid
    }

    // (almost) assignable; i.e., returns void instead of UserInt&
    // for extra robustness
    void operator= (const UserInt &rhs) {
        RW_ASSERT (ptr_     == &i_);                // verify *this is valid
        // verify rhs is valid
        RW_ASSERT (_RWSTD_CONST_CAST (const void*, rhs.ptr_) == &rhs.i_);
        RW_ASSERT (-1 <= i_     && i_     < 257);   // i may be invalid
        RW_ASSERT (-1 <  rhs.i_ && rhs.i_ < 257);   // rhs.i must ve valid

        i_ = rhs.i_;
    }

    static UserInt eof () {
        UserInt tmp;
        tmp.i_ = 256;   // EOF
        return tmp;
    }

    static UserInt from_char (const UserChar &c) {
        UserInt tmp;
        tmp.i_ = int (c.c);
        return tmp;
    }

    UserChar to_char () const {
        // working around an Intel C++ 9.1 bug #380635
        /* const */ UserChar tmp /* = { 0, i_ }*/;
        tmp.f = 0;
        tmp.c = (unsigned char)(i_);
        return tmp; 
    }

    ~UserInt () {
        RW_ASSERT (ptr_ == &i_);            // verify *this is valid
        RW_ASSERT (-1 <= i_ == i_ < 257);   // i may be invalid

        i_   = _RWSTD_INT_MIN;   // invalidate
        ptr_ = &ptr_;            // invalidate
    }

    bool equal (const UserInt &rhs) const {
        // verify *this is valid
        RW_ASSERT (_RWSTD_CONST_CAST (const void*, ptr_) == &i_);
        // verify rhs is valid
        RW_ASSERT (_RWSTD_CONST_CAST (const void*, rhs.ptr_) == &rhs.i_);
        RW_ASSERT (-1 < i_     && i_     < 257);   // i must ve valid
        RW_ASSERT (-1 < rhs.i_ && rhs.i_ < 257);   // rhs.i must be valid

        return i_ == rhs.i_;
    }
};


// user-defined character traits template
// (declared but not defined)
template <class charT>
struct UserTraits;


struct TraitsMemFunc
{
    enum {
        assign, eq, lt, compare, length, find, copy, move,
        assign2, not_eof, to_char_type, to_int_type, eq_int_type,
        eof,
        n_funs
    };
};


// required specialization on char
_RWSTD_SPECIALIZED_CLASS
struct _TEST_EXPORT UserTraits<char>: std::char_traits<char>
{
    typedef std::char_traits<char> Base;
    typedef Base::char_type        char_type;
    typedef Base::int_type         int_type;
    typedef TraitsMemFunc          MemFun;

    // avoid any dependency on the library
    typedef int                   off_type;     // std::streamoff
    typedef int                   state_type;   // std::mbstate_t
    typedef std::fpos<state_type> pos_type;     // std::fpos<state_type>

    static void
    assign (char_type&, const char_type&);

    static bool
    eq (const char_type&, const char_type&);

    static bool
    lt (const char_type&, const char_type&);

    static int
    compare (const char_type*, const char_type*, _RWSTD_SIZE_T);
        
    static _RWSTD_SIZE_T
    length (const char_type*);
 
    static const char_type*
    find (const char_type*, _RWSTD_SIZE_T, const char_type&);

    static char_type*
    copy (char_type*, const char_type*, _RWSTD_SIZE_T);

    static char_type*
    move (char_type*, const char_type*, _RWSTD_SIZE_T);

    static char_type*
    assign (char_type*, _RWSTD_SIZE_T, char_type);

    static int_type
    not_eof (const int_type&);

    static char_type
    to_char_type (const int_type&);
      
    static int_type
    to_int_type (const char_type&);

    static bool
    eq_int_type (const int_type&, const int_type&);

    static int_type
    eof ();

    static _RWSTD_SIZE_T n_calls_ [];

    static int_type eof_;

private:

    // not defined to detect bad assumptions made by the library
    UserTraits ();
    ~UserTraits ();
    void operator= (UserTraits&);
};


#ifndef _RWSTD_NO_WCHAR_T

// required specialization on wchar_t
_RWSTD_SPECIALIZED_CLASS
struct _TEST_EXPORT UserTraits<wchar_t>: std::char_traits<wchar_t>
{
    typedef std::char_traits<wchar_t> Base;
    typedef Base::char_type           char_type;
    typedef Base::int_type            int_type;
    typedef TraitsMemFunc             MemFun;

    // avoid any dependency on the library
    typedef int                   off_type;     // std::streamoff
    typedef int                   state_type;   // std::mbstate_t
    typedef std::fpos<state_type> pos_type;     // std::fpos<state_type>

    static void
    assign (char_type&, const char_type&);

    static bool
    eq (const char_type&, const char_type&);

    static bool
    lt (const char_type&, const char_type&);

    static int
    compare (const char_type*, const char_type*, _RWSTD_SIZE_T);
        
    static _RWSTD_SIZE_T
    length (const char_type*);
 
    static const char_type*
    find (const char_type*, _RWSTD_SIZE_T, const char_type&);

    static char_type*
    copy (char_type*, const char_type*, _RWSTD_SIZE_T);

    static char_type*
    move (char_type*, const char_type*, _RWSTD_SIZE_T);

    static char_type*
    assign (char_type*, _RWSTD_SIZE_T, char_type);

    static int_type
    not_eof (const int_type&);

    static char_type
    to_char_type (const int_type&);
      
    static int_type
    to_int_type (const char_type&);

    static bool
    eq_int_type (const int_type&, const int_type&);

    static int_type
    eof ();

    static _RWSTD_SIZE_T n_calls_ [];

    static int_type eof_;

private:

    // not defined to detect bad assumptions made by the library
    UserTraits ();
    ~UserTraits ();
    void operator= (UserTraits&);
};

#endif   // _RWSTD_NO_WCHAR_T


_RWSTD_SPECIALIZED_CLASS
struct _TEST_EXPORT UserTraits<UserChar>   // user-defined character traits
{
    typedef TraitsMemFunc MemFun;

    typedef UserChar char_type;
    typedef UserInt  int_type;

    // avoid any dependency on the library
    typedef int                   off_type;     // std::streamoff
    typedef int                   state_type;   // std::mbstate_t
    typedef std::fpos<state_type> pos_type;     // std::fpos<state_type>

    // accesses to the char_type::f member may trigger a SIGBUS
    // on some architectures (e.g., PA or SPARC) if the member
    // isn't appropriately aligned

    static void assign (char_type&, const char_type&);

    static bool eq (const char_type&, const char_type&);

    static bool lt (const char_type&, const char_type&);

    static int
    compare (const char_type*, const char_type*, _RWSTD_SIZE_T);
        
    static _RWSTD_SIZE_T length (const char_type*);
 
    static const char_type*
    find (const char_type*, _RWSTD_SIZE_T, const char_type&);

    static char_type*
    copy (char_type*, const char_type*, _RWSTD_SIZE_T);

    static char_type*
    move (char_type*, const char_type*, _RWSTD_SIZE_T);

    static char_type*
    assign (char_type*, _RWSTD_SIZE_T, char_type);

    static int_type not_eof (const int_type&);

    static char_type to_char_type (const int_type&);
      
    static int_type to_int_type (const char_type&);

    static bool eq_int_type (const int_type&, const int_type&);

    static int_type eof ();

    static _RWSTD_SIZE_T n_calls_ [];

private:

    // not defined to detect bad assumptions made by the library
    UserTraits ();
    ~UserTraits ();
    void operator= (UserTraits&);
};


// rw_widen() widens successive elements of src into the buffer dst
// when (dst != 0) the last character in the buffer is guaranteed to be NUL,
// regardless of the value of str [len]
// when (len == SIZE_MAX && src != 0), computes len as if by evaluating
// len = strlen(src)
// when (src == 0 && len < SIZE_MAX), initializes the first len elements
// of dst to NUL (i.e., such a call is the equivalent of calling
// memset(dst, 0, len * sizeof *dst))
// returns dst
_TEST_EXPORT char*
rw_widen (char*         /* dst */,
          const char*   /* src */,
          _RWSTD_SIZE_T /* len */ = _RWSTD_SIZE_MAX);

// rw_expand() interprets string src as a sequence of directives and
// widens the result of their processing into the provided buffer dst
// when (dst != 0), otherwise into a dynamically allocated buffer of
// sufficient size
// each directive consists of a character C, optionally followed by
// the '@' sign followed by a non-negative decimal number N; the result
// of the processing of a directive is N consecutive copies of the
// character C where (N = 1) when the '@' is absent
// when (dst_len != 0) the function sets *dst_len to the number of
// produced characters not counting the terminating NUL
// the function returns the dynamically allocated buffer; the caller
// must deallocate the buffer using the delete expression
_TEST_EXPORT char*
rw_expand (char*          /* dst     */,
           const char*    /* src     */,
           _RWSTD_SIZE_T  /* src_len */ = _RWSTD_SIZE_MAX,
           _RWSTD_SIZE_T* /* dst_len */ = 0);


// rw_narrow() narrows successive elements of src into the buffer dst
// (see rw_widen() for details)
_TEST_EXPORT char*
rw_narrow (char*         /* dst */,
           const char*   /* src */,
           _RWSTD_SIZE_T /* len */ = _RWSTD_SIZE_MAX);

// rw_match() compares up to len successive elements of s1 and s2 for
// equality until it finds a pair that do not compare equal or until
// len comparisons has been made
// if (len == SIZE_MAX) is true elements are compared until the first
// mismatch is found or until the NUL character is encountered
// returns the number of matching elements
_TEST_EXPORT _RWSTD_SIZE_T 
rw_match (const char*   /* s1  */,
          const char*   /* s2  */,
          _RWSTD_SIZE_T /* len */ = _RWSTD_SIZE_MAX);

#ifndef _RWSTD_WCHAR_T

_TEST_EXPORT wchar_t*
rw_widen (wchar_t*, const char*, _RWSTD_SIZE_T = _RWSTD_SIZE_MAX);

_TEST_EXPORT wchar_t*
rw_expand (wchar_t*       /* dst     */,
           const char*    /* src     */,
           _RWSTD_SIZE_T  /* src_len */ = _RWSTD_SIZE_MAX,
           _RWSTD_SIZE_T* /* dst_len */ = 0);

_TEST_EXPORT char*
rw_narrow (char*, const wchar_t*, _RWSTD_SIZE_T = _RWSTD_SIZE_MAX);

_TEST_EXPORT _RWSTD_SIZE_T
rw_match (const char*, const wchar_t*,
          _RWSTD_SIZE_T = _RWSTD_SIZE_MAX);

#endif   // _RWSTD_WCHAR_T

_TEST_EXPORT UserChar*
rw_widen (UserChar*, const char*, _RWSTD_SIZE_T = _RWSTD_SIZE_MAX);

_TEST_EXPORT UserChar*
rw_expand (UserChar*      /* dst     */,
           const char*    /* src     */,
           _RWSTD_SIZE_T  /* src_len */ = _RWSTD_SIZE_MAX,
           _RWSTD_SIZE_T* /* dst_len */ = 0);

_TEST_EXPORT char*
rw_narrow (char*, const UserChar*, _RWSTD_SIZE_T = _RWSTD_SIZE_MAX);

_TEST_EXPORT _RWSTD_SIZE_T
rw_match (const char*, const UserChar*, _RWSTD_SIZE_T = _RWSTD_SIZE_MAX);


// accessors to n_calls array, if present
template <class charT> 
inline _RWSTD_SIZE_T*
rw_get_call_counters (std::char_traits<charT>*, charT*)
{
    return 0;
}

template <class charT> 
inline _RWSTD_SIZE_T*
rw_get_call_counters (UserTraits<charT>*, charT*)
{
    return UserTraits<charT>::n_calls_;
}


static const struct _TEST_EXPORT UserCharFmatInit {
    UserCharFmatInit ();
} _rw_user_char_fmat_init;

#endif   // RW_CHAR_INCLUDED
