///////////////////////////////////////////////////////////////////////////////
//
//  The contents of this file are subject to the Mozilla Public License
//  Version 1.1 (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.mozilla.org/MPL/
//
//  Software distributed under the License is distributed on an "AS IS"
//  basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the
//  License for the specific language governing rights and limitations
//  under the License.
// 
//  The Original Code is MP4v2.
// 
//  The Initial Developer of the Original Code is Kona Blend.
//  Portions created by Kona Blend are Copyright (C) 2008.
//  Portions created by David Byron are Copyright (C) 2010.
//  All Rights Reserved.
//
//  Contributors:
//      Kona Blend, kona8lend@@gmail.com
//      David Byron, dbyron@dbyron.com
//
///////////////////////////////////////////////////////////////////////////////

#include "util/impl.h"

namespace mp4v2 { namespace util {
    using namespace itmf;

///////////////////////////////////////////////////////////////////////////////

class ArtUtility : public Utility
{
private:
    enum ArtLongCode {
        LC_ART_ANY = _LC_MAX,
        LC_ART_INDEX,
        LC_LIST,
        LC_ADD,
        LC_REMOVE,
        LC_REPLACE,
        LC_EXTRACT,
    };

public:
    ArtUtility( int, char** );

protected:
    // delegates implementation
    bool utility_option( int, bool& );
    bool utility_job( JobContext& );

private:
    struct ArtType {
        string         name;
        string         ext;
        std::vector<string> cwarns; // compatibility warnings
        string         cerror; // compatibility error
    };

    bool actionList    ( JobContext& );
    bool actionAdd     ( JobContext& );
    bool actionRemove  ( JobContext& );
    bool actionReplace ( JobContext& );
    bool actionExtract ( JobContext& );

    bool extractSingle( JobContext&, const CoverArtBox::Item&, uint32_t );

private:
    Group  _actionGroup;
    Group  _parmGroup;

    bool (ArtUtility::*_action)( JobContext& );

    string   _artImageFile;
    uint32_t _artFilter;
};

///////////////////////////////////////////////////////////////////////////////

ArtUtility::ArtUtility( int argc, char** argv )
    : Utility      ( "mp4art", argc, argv )
    , _actionGroup ( "ACTIONS" )
    , _parmGroup   ( "ACTION PARAMETERS" )
    , _action      ( NULL )
    , _artFilter   ( std::numeric_limits<uint32_t>::max() )
{
    // add standard options which make sense for this utility
    _group.add( STD_OPTIMIZE );
    _group.add( STD_DRYRUN );
    _group.add( STD_KEEPGOING );
    _group.add( STD_OVERWRITE );
    _group.add( STD_FORCE );
    _group.add( STD_QUIET );
    _group.add( STD_DEBUG );
    _group.add( STD_VERBOSE );
    _group.add( STD_HELP );
    _group.add( STD_VERSION );
    _group.add( STD_VERSIONX );

    _parmGroup.add( "art-any",   false, LC_ART_ANY,   "act on all covr-boxes (default)" );
    _parmGroup.add( "art-index", true,  LC_ART_INDEX, "act on covr-box index IDX", "IDX" );
    _groups.push_back( &_parmGroup );

    _actionGroup.add( "list",    false, LC_LIST,    "list all covr-boxes" );
    _actionGroup.add( "add",     true,  LC_ADD,     "add covr-box from IMG file", "IMG" );
    _actionGroup.add( "replace", true,  LC_REPLACE, "replace covr-box with IMG file", "IMG" );
    _actionGroup.add( "remove",  false, LC_REMOVE,  "remove covr-box" );
    _actionGroup.add( "extract", false, LC_EXTRACT, "extract covr-box" );
    _groups.push_back( &_actionGroup );

    _usage = "[OPTION]... ACTION file...";
    _description =
        // 79-cols, inclusive, max desired width
        // |----------------------------------------------------------------------------|
        "\nFor each mp4 (m4a) file specified, perform the specified ACTION. An action"
        "\nmust be specified. Some options are not applicable for some actions.";
}

///////////////////////////////////////////////////////////////////////////////

bool
ArtUtility::actionAdd( JobContext& job )
{
    File in( _artImageFile, File::MODE_READ );
    if( in.open() )
        return herrf( "unable to open %s for read: %s\n", _artImageFile.c_str(), sys::getLastErrorStr() );

    const uint32_t max = std::numeric_limits<uint32_t>::max();
    if( in.size > max )
        return herrf( "file too large: %s (exceeds %u bytes)\n", _artImageFile.c_str(), max );

    CoverArtBox::Item item;
    item.size     = static_cast<uint32_t>( in.size );
    item.buffer   = static_cast<uint8_t*>( malloc( item.size ));
    item.autofree = true;

    File::Size nin;
    if( in.read( item.buffer, item.size, nin ))
        return herrf( "read failed: %s\n", _artImageFile.c_str() );

    in.close();

    verbose1f( "adding %s -> %s\n", _artImageFile.c_str(), job.file.c_str() );
    if( dryrunAbort() )
        return SUCCESS;

    job.fileHandle = MP4Modify( job.file.c_str() );
    if( job.fileHandle == MP4_INVALID_FILE_HANDLE )
        return herrf( "unable to open for write: %s\n", job.file.c_str() );

    if( CoverArtBox::add( job.fileHandle, item ))
        return herrf( "unable to add covr-box\n" );

    return SUCCESS;
}

///////////////////////////////////////////////////////////////////////////////

bool
ArtUtility::actionExtract( JobContext& job )
{
    job.fileHandle = MP4Read( job.file.c_str() );
    if( job.fileHandle == MP4_INVALID_FILE_HANDLE )
        return herrf( "unable to open for read: %s\n", job.file.c_str() );

    // single-mode
    if( _artFilter != std::numeric_limits<uint32_t>::max() ) {
        CoverArtBox::Item item;
        if( CoverArtBox::get( job.fileHandle, item, _artFilter ))
            return herrf( "unable to retrieve covr-box (index=%d): %s\n", _artFilter, job.file.c_str() );

        return extractSingle( job, item, _artFilter );
    }

    // wildcard-mode
    CoverArtBox::ItemList items;
    if( CoverArtBox::list( job.fileHandle, items ))
        return herrf( "unable to fetch list of covr-box: %s\n", job.file.c_str() );

    bool onesuccess = false;
    const CoverArtBox::ItemList::size_type max = items.size();
    for( CoverArtBox::ItemList::size_type i = 0; i < max; i++ ) {
        bool rv = extractSingle( job, items[i], (uint32_t)i );
        if( !rv )
            onesuccess = true;
        if( !_keepgoing && rv )
            return FAILURE;
    }

    return _keepgoing ? onesuccess : SUCCESS;
}

///////////////////////////////////////////////////////////////////////////////

bool
ArtUtility::actionList( JobContext& job )
{
    ostringstream report;

    const int widx = 3;
    const int wsize = 8;
    const int wtype = 9;
    const string sep = "  ";

    if( _jobCount == 0 ) {
      report << std::setw(widx) << right << "IDX" << left << sep
             << std::setw(wsize) << right << "BYTES" << left << sep
             << std::setw(8) << "CRC32" << sep << std::setw(wtype) << "TYPE"
             << sep << std::setw(0) << "FILE" << '\n';

      report << std::setfill('-') << std::setw(70) << "" << std::setfill(' ')
             << '\n';
    }

    job.fileHandle = MP4Read( job.file.c_str() );
    if( job.fileHandle == MP4_INVALID_FILE_HANDLE )
        return herrf( "unable to open for read: %s\n", job.file.c_str() );

    CoverArtBox::ItemList items;
    if( CoverArtBox::list( job.fileHandle, items ))
        return herrf( "unable to get list of covr-box: %s\n", job.file.c_str() );

    int line = 0;
    const CoverArtBox::ItemList::size_type max = items.size();
    for( CoverArtBox::ItemList::size_type i = 0; i < max; i++ ) {
      if (_artFilter != std::numeric_limits<uint32_t>::max() && _artFilter != i)
        continue;

      CoverArtBox::Item& item = items[i];
      const uint32_t crc = crc32(item.buffer, item.size);

      report << std::setw(widx) << right << i << sep << std::setw(wsize)
             << item.size << sep << std::setw(8) << std::setfill('0')
             << std::hex << crc << std::setfill(' ') << std::dec << sep
             << std::setw(wtype) << left << enumBasicType.toString(item.type);

      if (line++ == 0) report << sep << std::setw(0) << job.file;

      report << '\n';
    }

    verbose1f( "%s", report.str().c_str() );
    return SUCCESS;
}

///////////////////////////////////////////////////////////////////////////////

bool
ArtUtility::actionRemove( JobContext& job )
{
    job.fileHandle = MP4Modify( job.file.c_str() );
    if( job.fileHandle == MP4_INVALID_FILE_HANDLE )
        return herrf( "unable to open for write: %s\n", job.file.c_str() );

    if( _artFilter == std::numeric_limits<uint32_t>::max() )
        verbose1f( "removing covr-box (all) from %s\n", job.file.c_str() );
    else
        verbose1f( "removing covr-box (index=%d) from %s\n", _artFilter, job.file.c_str() );

    if( dryrunAbort() )
        return SUCCESS;

    if( CoverArtBox::remove( job.fileHandle, _artFilter ))
        return herrf( "remove failed\n" );

    return SUCCESS;
}

///////////////////////////////////////////////////////////////////////////////

bool
ArtUtility::actionReplace( JobContext& job )
{
    File in( _artImageFile, File::MODE_READ );
    if( in.open() )
        return herrf( "unable to open %s for read: %s\n", _artImageFile.c_str(), sys::getLastErrorStr() );

    const uint32_t max = std::numeric_limits<uint32_t>::max();
    if( in.size > max )
        return herrf( "file too large: %s (exceeds %u bytes)\n", _artImageFile.c_str(), max );

    CoverArtBox::Item item;
    item.size     = static_cast<uint32_t>( in.size );
    item.buffer   = static_cast<uint8_t*>( malloc( item.size ));
    item.autofree = true;

    File::Size nin;
    if( in.read( item.buffer, item.size, nin ))
        return herrf( "read failed: %s\n", _artImageFile.c_str() );

    in.close();

    if( _artFilter == std::numeric_limits<uint32_t>::max() )
        verbose1f( "replacing %s -> %s (all)\n", _artImageFile.c_str(), job.file.c_str() );
    else
        verbose1f( "replacing %s -> %s (index=%d)\n", _artImageFile.c_str(), job.file.c_str(), _artFilter );

    if( dryrunAbort() )
        return SUCCESS;

    job.fileHandle = MP4Modify( job.file.c_str() );
    if( job.fileHandle == MP4_INVALID_FILE_HANDLE )
        return herrf( "unable to open for write: %s\n", job.file.c_str() );

    if( CoverArtBox::set( job.fileHandle, item, _artFilter ))
        return herrf( "unable to add covr-box: %s\n", job.file.c_str() );

    return SUCCESS;
}

///////////////////////////////////////////////////////////////////////////////

bool
ArtUtility::extractSingle( JobContext& job, const CoverArtBox::Item& item, uint32_t index )
{
    // compute out filename
    string out_name = job.file;
    FileSystem::pathnameStripExtension( out_name );

    ostringstream oss;
    oss << out_name << ".art[" << index << ']';

    // if implicit we try to determine type by inspecting data
    BasicType bt = item.type;
    if( bt == BT_IMPLICIT )
        bt = computeBasicType( item.buffer, item.size );

    // add file extension appropriate for known covr-box types
    switch( bt ) {
        case BT_GIF:    oss << ".gif"; break;
        case BT_JPEG:   oss << ".jpg"; break;
        case BT_PNG:    oss << ".png"; break;
        case BT_BMP:    oss << ".bmp"; break;

        default:
            oss << ".dat";
            break;
    }

    out_name = oss.str();
    verbose1f( "extracting %s (index=%d) -> %s\n", job.file.c_str(), index, out_name.c_str() );
    if( dryrunAbort() )
        return SUCCESS;

    File out( out_name, File::MODE_CREATE );
    if( openFileForWriting( out ))
        return FAILURE;

    File::Size nout;
    if( out.write( item.buffer, item.size, nout ))
        return herrf( "write failed: %s\n", out_name.c_str() );

    out.close();
    return SUCCESS;
}

///////////////////////////////////////////////////////////////////////////////

bool
ArtUtility::utility_job( JobContext& job )
{
    if( !_action )
        return herrf( "no action specified\n" );

    return (this->*_action)( job );
}

///////////////////////////////////////////////////////////////////////////////

bool
ArtUtility::utility_option( int code, bool& handled )
{
    handled = true;

    switch( code ) {
        case LC_ART_ANY:
            _artFilter = std::numeric_limits<uint32_t>::max();
            break;

        case LC_ART_INDEX:
        {
            istringstream iss( prog::optarg );
            iss >> _artFilter;
            if( iss.rdstate() != ios::eofbit )
                return herrf( "invalid cover-art index: %s\n", prog::optarg );
            break;
        }

        case LC_LIST:
            _action = &ArtUtility::actionList;
            break;

        case LC_ADD:
            _action = &ArtUtility::actionAdd;
            _artImageFile = prog::optarg;
            if( _artImageFile.empty() )
                return herrf( "invalid image file: empty-string\n" );
            break;

        case LC_REMOVE:
            _action = &ArtUtility::actionRemove;
            break;

        case LC_REPLACE:
            _action = &ArtUtility::actionReplace;
            _artImageFile = prog::optarg;
            if( _artImageFile.empty() )
                return herrf( "invalid image file: empty-string\n" );
            break;

        case LC_EXTRACT:
            _action = &ArtUtility::actionExtract;
            break;

        default:
            handled = false;
            break;
    }

    return SUCCESS;
}

///////////////////////////////////////////////////////////////////////////////

}} // namespace mp4v2::util

///////////////////////////////////////////////////////////////////////////////

extern "C"
int main( int argc, char** argv )
{
    mp4v2::util::ArtUtility util( argc, argv );
    return util.process();
}
