void UnitFactory::addMissileBuffer( NetBuffer &netbuf,
                                    const string &filename,
                                    const string &name,
                                    const string &fullname,
                                    int faction,
                                    const string &modifications,
                                    const ClientState &curr_state,
                                    const float damage,
                                    float phasedamage,
                                    float time,
                                    float radialeffect,
                                    float radmult,
                                    float detonation_radius,
                                    ObjSerial netcreate )
{
    netbuf.addChar( ZoneMgr::AddMissile );
    netbuf.addSerial( netcreate );
    netbuf.addString( filename );
    netbuf.addString( name );
    netbuf.addString( fullname );

    netbuf.addInt32( faction );
    netbuf.addString( modifications );
    netbuf.addFloat( damage );
    netbuf.addFloat( phasedamage );
    netbuf.addFloat( time );
    netbuf.addFloat( radialeffect );
    netbuf.addFloat( radmult );
    netbuf.addFloat( detonation_radius );
    if (netbuf.version() <= 4951)
        netbuf.addTransformation( curr_state.getTransformation() );
    else
        netbuf.addClientState( curr_state );
}
int NetClient::loginAuth( string str_callsign, string str_passwd, string &error )
{
    COUT<<"enter "<<"NetClient::loginLoop"<<endl;
    lastsave.clear();
    ship_select_list.clear();

    Packet    packet2;
    NetBuffer netbuf;

    //memset( buffer, 0, tmplen+1);
    netbuf.addString( str_callsign );
    netbuf.addString( str_passwd );

    packet2.send( CMD_LOGIN, 0,
                 netbuf.getData(), netbuf.getDataLength(),
                 SENDRELIABLE, NULL, *this->clt_tcp_sock,
                 __FILE__, PSEUDO__LINE__( 316 ) );
    COUT<<"Sent login for player <"<<str_callsign<<">:<*******"
        <<">"<<endl
        <<"   - buffer length : "<<packet2.getDataLength()<<endl;
    this->callsign = str_callsign;
    this->password = str_passwd;
    //Now the loop
    return loginLoop( error );
}
void UnitFactory::addUnitBuffer( NetBuffer &netbuf,
                                 const string &filename,
                                 const string &name,
                                 const string &fullname,
                                 bool SubUnit,
                                 int faction,
                                 std::string customizedUnit,
                                 const ClientState &curr_state,
                                 Flightgroup *flightgroup,
                                 int fg_subnumber,
                                 string *netxml,
                                 ObjSerial netcreate )
{
    netbuf.addChar( ZoneMgr::AddUnit );
    assert( netcreate != 0 );           //crash if we are doing something stupid :)
    netbuf.addSerial( netcreate );
    netbuf.addString( filename );
    netbuf.addString( name );
    netbuf.addString( fullname );
    netbuf.addChar( SubUnit );
    netbuf.addInt32( faction );
    netbuf.addString( flightgroup != NULL ? flightgroup->name : std::string( "Object" ) );
    netbuf.addString( customizedUnit );
    netbuf.addInt32( fg_subnumber );
    if (netbuf.version() <= 4951)
        netbuf.addTransformation( curr_state.getTransformation() );
    else
        netbuf.addClientState( curr_state );
}
int NetClient::authenticate()
{
    COUT<<" enter "<<__PRETTY_FUNCTION__<<endl;

    Packet    packet2;
    string    str_callsign, str_passwd;
    NetBuffer netbuf;

    //Get the name and password from vegastrike.config
    //Maybe someday use a default Guest account if no callsign or password is provided thus allowing
    //Player to wander but not interact with the universe
    this->callsign = str_callsign = vs_config->getVariable( "player", "callsign", "" );
    this->password = str_passwd = vs_config->getVariable( "player", "password", "" );
    if ( global_username.length() )
        this->callsign = global_username;
    if ( global_password.length() )
        this->password = global_password;
    if ( str_callsign.length() && str_passwd.length() ) {
        netbuf.addString( str_callsign );
        netbuf.addString( str_passwd );

        packet2.send( CMD_LOGIN, 0,
                     netbuf.getData(), netbuf.getDataLength(),
                     SENDRELIABLE, NULL, *this->clt_tcp_sock,
                     __FILE__, PSEUDO__LINE__( 165 ) );
        COUT<<"Send login for player <"<<str_callsign<<">:<*******"
        "> - buffer length : "<<packet2.getDataLength()
            <<" (+"<<packet2.getHeaderLength()<<" header len"<<endl;
    } else {
        cerr<<"Callsign and/or password not specified in vegastrike.config, please check this."<<endl<<endl;
        return -1;
    }
    return 0;
}
void UnitFactory::addPlanetBuffer( NetBuffer &netbuf,
                                   QVector x,
                                   QVector y,
                                   float vely,
                                   const Vector &rotvel,
                                   float pos,
                                   float gravity,
                                   float radius,
                                   const char *filename,
                                   BLENDFUNC sr,
                                   BLENDFUNC ds,
                                   const vector< string > &dest,
                                   const QVector &orbitcent,
                                   Unit *parent,
                                   const GFXMaterial &ourmat,
                                   const std::vector< GFXLightLocal > &ligh,
                                   int faction,
                                   string fullname,
                                   bool inside_out,
                                   ObjSerial netcreate )
{
    netbuf.addChar( ZoneMgr::AddPlanet );
    netbuf.addSerial( netcreate );
    netbuf.addQVector( x );
    netbuf.addQVector( y );
    netbuf.addFloat( vely );
    netbuf.addVector( Vector( rotvel ) );
    netbuf.addFloat( pos );
    netbuf.addFloat( gravity );
    netbuf.addFloat( radius );

    netbuf.addString( string( filename ) );
    netbuf.addChar( sr );
    netbuf.addChar( ds );

    netbuf.addShort( dest.size() );
    for (unsigned int i = 0; i < dest.size(); i++)
        netbuf.addString( dest[i] );
    netbuf.addQVector( QVector( orbitcent ) );
    netbuf.addSerial( parent->GetSerial() );
    netbuf.addGFXMaterial( ourmat );
    netbuf.addShort( ligh.size() );
    for (unsigned int j = 0; j < ligh.size(); j++)
        netbuf.addGFXLightLocal( ligh[j] );
    netbuf.addInt32( faction );
    netbuf.addString( fullname );
    netbuf.addChar( inside_out );
}
void UnitFactory::addAsteroidBuffer( NetBuffer &netbuf,
                                     const char *filename,
                                     int faction,
                                     Flightgroup *fg,
                                     int fg_snumber,
                                     float difficulty,
                                     ObjSerial netcreate )
{
    netbuf.addChar( ZoneMgr::AddAsteroid );
    netbuf.addSerial( netcreate );
    netbuf.addString( string( filename ) );
    netbuf.addInt32( faction );
    netbuf.addString( fg->name );
    netbuf.addInt32( fg_snumber );
    netbuf.addFloat( difficulty );
}
void UnitFactory::addNebulaBuffer( NetBuffer &netbuf,
                                   const char *unitfile,
                                   bool SubU,
                                   int faction,
                                   Flightgroup *fg,
                                   int fg_snumber,
                                   ObjSerial netcreate )
{
    netbuf.addChar( ZoneMgr::AddNebula );
    netbuf.addSerial( netcreate );
    netbuf.addString( string( unitfile ) );
    netbuf.addChar( SubU );
    netbuf.addInt32( faction );
    netbuf.addString( fg->name );
    netbuf.addInt32( fg_snumber );
}
void NetClient::textMessage( const std::string &data )
{
    Packet    packet2;
    NetBuffer netbuf;
    netbuf.addString( data );
    //No data.
    packet2.send( CMD_TXTMESSAGE, 0,
                 netbuf.getData(), netbuf.getDataLength(),
                 SENDRELIABLE, NULL, *this->clt_tcp_sock,
                 __FILE__, PSEUDO__LINE__( 165 ) );
}
/*
 ************************************************************
 **** Create a new character                              ***
 ************************************************************
 */
bool NetClient::selectShip( unsigned int ship )
{
    if (lastsave.empty() || lastsave[0] == "") {
        NetBuffer netbuf;
        string    shipname;
        netbuf.addShort( (unsigned short) ship );
        if ( ship < ship_select_list.size() )
            shipname = ship_select_list[ship];
        netbuf.addString( shipname );
        Packet p;
        p.send( CMD_CHOOSESHIP, 0, netbuf.getData(), netbuf.getDataLength(), SENDRELIABLE,
               NULL, *clt_tcp_sock, __FILE__, PSEUDO__LINE__( 628 ) );
        string err;
        int    ret = loginLoop( err );
        if (ret != 1 || lastsave.size() < 2 || lastsave[0] == "") {
            cout<<"Error in CHOOSEHIP: "<<err
                <<"choice="<<ship<<"("<<shipname<<"), max="<<ret<<endl;
            return false;
        }
    }
    return true;
}
void NetServer::sendLoginAccept( ClientPtr clt, Cockpit *cp )
{
    COUT<<"enter "<<__PRETTY_FUNCTION__<<endl;
    //Verify that client already has a character
    NetBuffer netbuf;
    Unit     *un = cp->GetParent();
    if (!un) {
        sendLoginError( clt );
        return;
    }
    //Put the save parts in buffers in order to load them properly
    netbuf.Reset();

    string datestr = _Universe->current_stardate.GetFullTrekDate();
    netbuf.addString( datestr );
    netbuf.addString( clt->savegame[0] );
    netbuf.addString( clt->savegame[1] );

    Packet    packet2;

    //Create a cockpit for the player and parse its savegame
    ObjSerial cltserial = un->GetSerial();

    COUT<<">>> SEND LOGIN ACCEPT =( serial #"<<cltserial<<" )= --------------------------------------"<<endl;
    COUT<<"SAVE="<<clt->savegame[0].length()<<" bytes - XML="<<clt->savegame[1].length()<<" bytes"<<endl;
    cerr<<"SENDING STARDATE : "<<datestr<<endl;
    //Add the initial star system filename + hash if crypto++ support too
    string sysname = cp->savegame->GetStarSystem();
    string relsys  = sysname+".system";
    netbuf.addString( relsys );

    //Generate the starsystem before addclient so that it already contains serials
    StarSystem    *sts    = zonemgr->addZone( sysname );

#ifdef CRYPTO
    unsigned char *digest = new unsigned char[FileUtil::Hash.DigestSize()];
    string sysxml;
    if ( !( sysxml = zonemgr->getSystem( relsys ) ).empty() )
        FileUtil::HashStringCompute( sysxml, digest );
    else if ( !sysname.empty() )
        FileUtil::HashFileCompute( relsys, digest, SystemFile );
    netbuf.addShort( FileUtil::Hash.DigestSize() );
    netbuf.addBuffer( digest, FileUtil::Hash.DigestSize() );
    delete[] digest;
#else
    netbuf.addShort( 0 );
#endif

    int zoneid = _Universe->StarSystemIndex( sts );
    netbuf.addShort( zoneid );

    //Add system string to packet...
    //Long, I know, but is there any other way to keep all the proper graphics-related data that the server discards?
    //netbuf.addString( zonemgr->getSystem(sysname) );

    packet2.send( LOGIN_ACCEPT, cltserial, netbuf.getData(),
                 netbuf.getDataLength(), SENDRELIABLE, &clt->cltadr, clt->tcp_sock, __FILE__, PSEUDO__LINE__( 241 ) );
    //Now that we have a starsystem, we will want to make a mission.
    if (Mission::getNthPlayerMission( _Universe->whichPlayerStarship( un ), 0 ) == NULL) {
        if (active_missions.size() == 1)
            active_missions[0]->DirectorInitgame();
        //Make a mission specially for this cockpit.
        unsigned int oldcp = _Universe->CurrentCockpit();
        _Universe->SetActiveCockpit( cp );
        _Universe->pushActiveStarSystem( _Universe->AccessCockpit()->activeStarSystem );
        LoadMission( "", vs_config->getVariable( "server", "serverscript", "import server;my_obj=server.player()" ), false );
        _Universe->popActiveStarSystem();
        _Universe->SetActiveCockpit( oldcp );
    }
}