//
// LDASTools AL - A library collection to provide an abstraction layer
//
// Copyright (C) 2018 California Institute of Technology
//
// LDASTools AL is free software; you may redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 (GPLv2) of the
// License or at your discretion, any later version.
//
// LDASTools AL is distributed in the hope that it will be useful, but
// without any warranty or even the implied warranty of merchantability
// or fitness for a particular purpose. See the GNU General Public
// License (GPLv2) for more details.
//
// Neither the names of the California Institute of Technology (Caltech),
// The Massachusetts Institute of Technology (M.I.T), The Laser
// Interferometer Gravitational-Wave Observatory (LIGO), nor the names
// of its contributors may be used to endorse or promote products derived
// from this software without specific prior written permission.
//
// You should have received a copy of the licensing terms for this
// software included in the file LICENSE located in the top-level
// directory of this package. If you did not, you can view a copy at
// http://dcc.ligo.org/M1500244/LICENSE
//

#include "ldastoolsal/Config.hh"

#include <algorithm>
#include <cctype>
#include <functional>
#include <iostream>
#include <locale>
#include <string>
#include <sstream>

namespace
{
    static inline std::string&
    ltrim( std::string& s )
    {
        s.erase( s.begin( ),
                 std::find_if( s.begin( ), s.end( ), []( unsigned char ch ) {
                     return !std::isspace( ch );
                 } ) );
        return s;
    }

    static inline std::string&
    rtrim( std::string& s )
    {
        s.erase( std::find_if(
                     s.rbegin( ),
                     s.rend( ),
                     []( unsigned char ch ) { return !std::isspace( ch ); } )
                     .base( ),
                 s.end( ) );
        return s;
    }

    static inline std::string&
    trim( std::string& s )
    {
        return ltrim( rtrim( s ) );
    }
} // namespace

namespace LDASTools
{
    namespace AL
    {
        Config::Config( )
        {
        }

        void
        Config::Parse( std::istream& Stream )
        {
            std::string line;

            while ( std::getline( Stream, line ) )
            {
                line = trim( line );
                std::string::size_type pos;

                if ( line.empty( ) || ( *( line.begin( ) ) == '#' ) )
                {
                    // This is a comment
                    continue;
                }
                else if ( ( *( line.begin( ) ) == '[' ) &&
                          ( *( line.end( ) - 1 ) == ']' ) )
                {
                    line = line.substr( 1, line.size( ) - 2 );
                    line = trim( line );
                    ParseBlock( line );
                }
                else if ( ( pos = line.find( '=' ) ) != std::string::npos )
                {
                    std::istringstream is_line( trim( line ) );
                    std::string        key;
                    std::string        value;

                    std::getline( is_line, key, '=' );
                    std::getline( is_line, value );
                    ParseKeyValue( trim( key ), trim( value ) );
                }
                else
                {
                    ParseWord( line );
                }
            }
        }
    } // namespace AL
} // namespace LDASTools
