/***********************************************************************
**
**   hwinfo.cpp
**
**   This file is part of Cumulus
**
************************************************************************
**
**   Copyright (c):  2004 by Eckhard Völlm
**
**   This file is distributed under the terms of the General Public
**   Licence. See the file COPYING for more information.
**
**   $Id: hwinfo.cpp,v 1.13 2005/02/13 14:56:40 axel Exp $
**
***********************************************************************/

#include <qfile.h>
#include <qtextstream.h>
#include <qstring.h>
#include <qglobal.h>
#include <malloc.h>
#include "hwinfo.h"


HwInfo * HwInfo::theInstance = 0;

HwInfo::HwInfo()
{
    // Readout Hardware information and initialize variables
    _hwType = unknown;
    _hwString=QString("");

    QFile f( PATH_PROC_CPUINFO );
    if ( f.open( IO_ReadOnly ) )
    {
        QTextStream s( &f );
        while ( !s.atEnd() )
        {
            QString line ( s.readLine() );
            if ( line.startsWith( "Hardware" ) )
            {
                _hwString=line.mid(line.find(":")).stripWhiteSpace();
                qDebug( "HW - found '%s'", (const char*) line);
                if      ( line.contains( "sharp", false ) )   _hwType = sharp;
                else if ( line.contains( "ipaq", false ) )    _hwType = ipaq;
                else if ( line.contains( "simpad", false ) )  _hwType = simpad;
                else if ( line.contains( "jornada", false ) ) _hwType = journada;
                else if ( line.contains( "ramses", false ) )  _hwType = ramses;
                break;
            }
        }
    }
    else
    {
        qWarning( "- can't open '%s' ",PATH_PROC_CPUINFO  );
    }
    if( _hwType == unknown )
    { qWarning( " - unknown PDA hardware - using default: desktop" );
        _hwType = desktop;
        if (_hwString.isEmpty()) _hwString="UNKNOWN";
    }

}


HwInfo::~HwInfo()
{
    // Singleton lives till power off...
}

HwInfo * HwInfo::instance( void )
{
    // First user will create it
    if( theInstance == 0 )
        theInstance = new HwInfo;
    return( theInstance );
};

int HwInfo::getFreeMemory() {
    int a=0, res=0, posStart=0, posEnd=0;
    QFile f( PATH_PROC_MEMINFO );
    if ( f.open( IO_ReadOnly ) )
    {
        QTextStream s( &f );
        while ( !s.atEnd() )
        {
            QString line ( s.readLine() );
            if ( line.startsWith( "MemFree" ) || line.startsWith( "Buffers" ) || line.startsWith( "Cached" ) )
            {
                posStart=line.find(':');
                posEnd=line.find(" kB");
                a=line.mid(posStart+1,posEnd-posStart).stripWhiteSpace().toInt();
//                qDebug( "Usable memory: '%d' (found in string: '%s' taken from line '%s')", a, line.mid(posStart+1,posEnd-posStart).stripWhiteSpace().latin1(), line.latin1());
                res+=a;
            }
        }
    }
    else
    {
        qWarning( "- can't open '%s' ",PATH_PROC_MEMINFO  );
    }
    if( res == 0 )
    {
        qWarning( "No usable memory info found, assuming 1 MB free." );
        res=1024;
    } else {
        //qDebug("Usable memory found: %d kB", res);
    }

    //get free heap space
    struct mallinfo m = mallinfo();
    //qDebug ("  fordblks: %d (%d KB)\n  uordblks: %d\n  hblkhd: %d\nTotal used: %d; total allocated: %d", m.fordblks, m.fordblks/1024,m.uordblks, m.hblkhd, m.uordblks+m.hblkhd,  m.uordblks+m.hblkhd+m.fordblks);
    //add the free space on the heap to the total free space, minus the fragmentation factor
    int heapfree=m.fordblks/1024;
    // qDebug("free heapspace: %d KB", heapfree);
    if (heapfree > HEAP_FRAGMENTATION_FACTOR) res += heapfree - HEAP_FRAGMENTATION_FACTOR;

    return res;
}

const QString HwInfo::getCfDevice( void ) {
    qDebug("Detecting serial device for CF card...");
    int posStart;
    QString res("/dev/ttyS3");
    QFile f( PATH_CF_INFO );

    if( ! f.exists() )
      {
	f.setName( PATH_CF_INFO1);
      }

    if ( f.open( IO_ReadOnly ) )
    {
        QTextStream s( &f );
        while ( !s.atEnd() )
        {
            QString line ( s.readLine() );
            if ( line.startsWith( "0" ) )
            {
	      posStart=line.find("ttyS");
                res="/dev/" + line.mid(posStart,6).stripWhiteSpace();
                qDebug("CF-Card device %s found.", res.latin1());
            }
        }
	f.close();
    }
    else
    {
      qWarning( "HwInfo::getCfDevice: Can't open '%s', reverting to default", f.name().latin1()  );
    }
    return res;
}
