/***************************************************************************
 *   Copyright (C) 2005 by Pawel Nawrocki                                  *
 *   pnawrocki@interia.pl                                                  *
 *                                                                         *
 *   This program is free software; you can 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 of the License, or     *
 *   (at your option) any later version.                                   *
 *                                                                         *
 *   This program is distributed in the hope that it will be useful,       *
 *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
 *   GNU General Public License for more details.                          *
 *                                                                         *
 *   You should have received a copy of the GNU General Public License     *
 *   along with this program; if not, write to the                         *
 *   Free Software Foundation, Inc.,                                       *
 *   51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.             *
 ***************************************************************************/

#ifndef WA_NETPARAMS_H
#define WA_NETPARAMS_H

#include <iostream>
#include <tqfile.h>
#include <tdemessagebox.h>
#include <tdelocale.h>

class WANetParams
{
public:
        TQString iface;
        TQString essid;
        //TQString mode;
        TQString channel;
        TQString ap;
        bool wep;
        TQString wepMode;
        TQString wepKey;
	bool wpa;
	TQStringList wpaSettings;
	TQString wpaKey;

        bool dhcp;
        TQString ip;
        TQString netmask;
        TQString broadcast;
        TQString gateway;
        TQString domain;
        TQString dns1;
        TQString dns2;

        bool hiddenEssid;
        bool wasHiddenEssid;
        bool wasWep;

	TQString preConnectionCommand;
	TQString postConnectionCommand;
	TQString preDisconnectionCommand;
	TQString postDisconnectionCommand;
	int preConnectionTimeout;
	int postConnectionTimeout;
	int preDisconnectionTimeout;
	int postDisconnectionTimeout;
	bool preConnectionDetached;
	bool postConnectionDetached;
	bool preDisconnectionDetached;
	bool postDisconnectionDetached;

        bool review()
        {
                bool r = false; //DEFAULTS TO 'no review needed'
                if (wep)
                        if ( (wepMode.isEmpty()) || (wepKey.isEmpty()) ) {
                                if (!wasWep) {
                                        KMessageBox::information(0, i18n("<qt><p>The network changed its security settings.</p><p>Please go to <i>Security</i> tab of the following dialog and configure WEP settings.</p></qt>") );
                                } else
                                        KMessageBox::error(0, i18n("<qt><p>Your WEP Key is not set properly.</p><p>Please go to <i>Security</i> tab of the following dialog and enter the required key.</p></qt>") );
                                r = true;
                        }
                if ( (hiddenEssid) && (!wasHiddenEssid) )
                        if ( KMessageBox::questionYesNo(0, i18n("<qt><p>The network has stopped broadcasting its ESSID since the last time you were connected.</p><p>Would you like to use '<b>%1</b>' as an ESSID for this network?</p><p><i>NOTE: If you answer No, a dialog will appear where you will be able to specify a different ESSID.</i></p></qt>").arg(essid) ) != 3 ) // !=YES
                                r = true;

                wasHiddenEssid = hiddenEssid;
                wasWep = wep;
                return r;
        }

        TQString netParamsString()
        {
                TQStringList mNPS;
                mNPS << boolToString(hiddenEssid) << essid << ap << channel << boolToString(wep) << wepMode << wepKey << boolToString(dhcp) << ip << netmask << broadcast << gateway << domain << dns1 << dns2 << boolToString(wasHiddenEssid) << boolToString(wasWep) << \
		preConnectionCommand << TQString::number(preConnectionTimeout) << boolToString(preConnectionDetached) << \
		postConnectionCommand << TQString::number(postConnectionTimeout) << boolToString(postConnectionDetached) << \
		preDisconnectionCommand << TQString::number(preDisconnectionTimeout) << boolToString(preDisconnectionDetached) << \
		postDisconnectionCommand << TQString::number(postDisconnectionTimeout) << boolToString(postDisconnectionDetached) << \
		wpaSettings.join(",") << wpaKey;
                return mNPS.join(",");
        }

        void loadNetParamsString( const TQString & nps )
        {
                /*if (nps.section(",",0,0)=="true")
                        hiddenEssid=true;
                else
                        hiddenEssid=false;*/	// COMMENTED OUT because hiddenEssid boolean is set from the list item
                essid = nps.section(",",1,1);
                ap = nps.section(",",2,2);
                //channel = nps.section(",",3,3);	COMMENTED OUT because channel is set from the list item
                /*if (nps.section(",",4,4)=="true")
                	wep=true;
                else
                	wep=false;*/	// COMMENTED OUT because wep boolean is set from the list item
                wepMode = nps.section(",",5,5);
                wepKey = nps.section(",",6,6);
		dhcp = ( nps.section(",",7,7) == "true" );
                ip = nps.section(",",8,8);
                netmask = nps.section(",",9,9);
                broadcast = nps.section(",",10,10);
                gateway = nps.section(",",11,11);
                domain = nps.section(",",12,12);
                dns1 = nps.section(",",13,13);
                dns2 = nps.section(",",14,14);
		wasHiddenEssid = ( nps.section(",",15,15)=="true" );
		wasWep = ( nps.section(",",16,16)=="true" );

		preConnectionCommand = nps.section(",",17,17);
		preConnectionTimeout = nps.section(",",18,18).toInt();
		preConnectionDetached = ( nps.section(",",19,19) == "true" );

		postConnectionCommand = nps.section(",",20,20);
		postConnectionTimeout = nps.section(",",21,21).toInt();
		postConnectionDetached = ( nps.section(",",22,22) == "true" );

		preDisconnectionCommand = nps.section(",",23,23);
		preDisconnectionTimeout = nps.section(",",24,24).toInt();
		preDisconnectionDetached = ( nps.section(",",25,25) == "true" );

		postDisconnectionCommand = nps.section(",",26,26);
		postDisconnectionTimeout = nps.section(",",27,27).toInt();
		postDisconnectionDetached = ( nps.section(",",28,28) == "true" );
		wpaSettings = TQStringList::split( ",", nps.section(",",29,32) ); // 4 fields
		wpaKey = nps.section(",",33,33);

        }
private:
        TQString boolToString( bool b )
        {
                TQString result;
                b ? result = "true" : result = "false";
                return result;
        }
};

class WACommands
{
public:
        bool allFound;
        TQStringList notFound;

        void init()
        {
                TQStringList binDirs;
                binDirs << "/sbin" << "/usr/sbin" << "/usr/local/sbin" << "/bin" << "/usr/bin" << "/usr/local/bin";

		wpa_supplicant = getPath("wpa_supplicant", binDirs);
		wpa_cli = getPath("wpa_cli", binDirs);
                dhcp = getPath("dhcpcd", binDirs); //these 2 checks have to be first, so allFound flag is properly set.
                if (dhcp.isEmpty())
                        dhcp = getPath("dhclient", binDirs);
                if (!dhcp.isEmpty()) {
                        allFound=1;
                        dhcpClient = dhcp.section("/",-1,-1);
                        std::cout << "DHCP Client: " << dhcpClient.ascii() << std::endl;
                }

                ifconfig = getPath("ifconfig", binDirs);
                iwconfig = getPath("iwconfig", binDirs);
                iwlist = getPath("iwlist", binDirs);
                route = getPath("route", binDirs);
                pidof = getPath("pidof", binDirs);

                if (!allFound)
                        std::cout << "Executable(s) not found:" << notFound.join(", ").ascii() << std::endl;
                else
                        std::cout << "All executables found." << std::endl;
        }

        TQStringList cmd( const TQString & action, const WANetParams & np, const bool & quiet = false )
        {
                TQStringList mCmd;

                /*if (action=="ifup")
                        mCmd << ifconfig << np.iface << "up";

                else if (action=="ifdown")
                        mCmd << ifconfig << np.iface << "down";

                else*/ if (action=="radio_on")
                        mCmd << iwconfig << np.iface << "txpower" << "auto";

                else if (action=="scan")
                        mCmd << iwlist << np.iface << "scan";

                else if (action=="disconnect")
                        mCmd << iwconfig << np.iface << "mode" << "managed" << "key" << "off" << "ap" << "off" << "essid" << "off";

                else if (action=="iwconfig_set") {
                        mCmd << iwconfig << np.iface << "mode" << "managed";
                        if (np.channel.toInt()>0)
                        	mCmd << "channel" << np.channel;
                        mCmd << "key";
                        if (np.wep && !np.wepKey.isEmpty())
                                mCmd << np.wepMode << np.wepKey;
                        else
                                mCmd << "off";
			mCmd << "essid" << np.essid;

                } else if (action=="iwconfig_ap") {
                        mCmd << iwconfig << np.iface << "ap" << np.ap;

                } else if (action=="ifconfig_dhcp") {
                        if (dhcpClient=="dhcpcd")
                                mCmd << dhcp << "-nd" << np.iface;
                        else if (dhcpClient=="dhclient")
                                mCmd << dhcp << np.iface; // << "-1" << "-q"

                } else if (action=="kill_dhcp") {
                        if ( dhcpClient=="dhcpcd")	//dhcpcd
                                mCmd << dhcp << "-k" << np.iface;
                        else //dhclient
                                mCmd << dhcp << "-r" << np.iface;

                } else if (action=="ifconfig_manual") {
                        mCmd << ifconfig << np.iface << np.ip;
                        if (!np.netmask.isEmpty())
                                mCmd << "netmask" << np.netmask;
                        if (!np.broadcast.isEmpty())
                                mCmd << "broadcast" << np.broadcast;

                } else if (action=="route_add") {
                        if (!np.gateway.isEmpty())
                                mCmd << route << "add" << "default" << "gw" << np.gateway;

                } else if (action=="route_del") {
                        if (!np.gateway.isEmpty())
                                mCmd << route << "del" << "default" << "gw" << np.gateway;

                } else
                        std::cout << "Unknown action: " << action.ascii() << std::endl;

                if ( (!mCmd.isEmpty()) && (!quiet) ) {//mCmd = TQStringList();
			TQString mCmdString = mCmd.join(" ");
			if (!np.wepKey.isEmpty()) mCmdString.replace(np.wepKey, "xxxxxxxxxx");
                        std::cout << action.ascii() << ": " << mCmdString.ascii() << std::endl;
		}
                return mCmd;
        }

	TQString route;
	TQString dhcpClient;
	TQString wpa_supplicant;
	TQString wpa_cli;
private:
        TQString ifconfig;
        TQString iwconfig;
        TQString iwlist;
        TQString dhcp;
        TQString pidof;

        TQString getPath(TQString file, TQStringList dirs)
        {
                TQString s;
                for ( TQStringList::Iterator it = dirs.begin(); it != dirs.end(); it++ ) {
                        if (TQFile( TQString(*it+"/"+file) ).exists()) {
                                s = TQString(*it+"/"+file);
                                break;
                        }
                }
                if (s.isEmpty()) {
                        allFound = 0;
                        notFound << file;
                }
                return s;
        }
};

#endif //WA_NETPARAMS_H
