Ejemplo n.º 1
0
        public void Start(TcpClient RClient, Server server)
        {
            //Test
                rTcpClient = RClient;

                reader = new BinaryReader(rTcpClient.GetStream());
                writer = new BinaryWriter(rTcpClient.GetStream());
                int failedTries = 0;
                byte[] OpCodePacket= new byte[1];
                int bytesRead;

                while (true)
                {
                    bytesRead = 0;

                    try
                    {
                        //blocks until a client sends a message
                        bytesRead = rTcpClient.Client.Receive(OpCodePacket,1,SocketFlags.None);
                        switch((RemoteProtocol)OpCodePacket[0])
                        {
                            case RemoteProtocol.Username: //Username
                                {
                                    Username = reader.ReadString();
                                    writer.Write((byte)RemoteProtocol.ServerMessage);
                                    writer.Write((byte)3);
                                    writer.Write("Hello "+Username+". Please enter the password sent to you by the bot owner to use the bot.");
                                    break;
                                }

                            case RemoteProtocol.Password:
                                {
                                    if(Username == null) throw new SocketException(-1);
                                    if(failedTries > 3)
                                    {
                                        writer.Write((byte)RemoteProtocol.ServerMessage);
                                        writer.Write((byte)2);
                                        writer.Write("You have incorrectly guessed the password more than three times. The session has been closed.");
                                        throw new SocketException(-1);
                                    }

                                    string Password = reader.ReadString();
                                    if(server._password != Password)
                                    {
                                        writer.Write((byte)RemoteProtocol.ServerMessage);
                                        writer.Write((byte)4);
                                        writer.Write("Incorrect password. You have " + (3 - failedTries).ToString() + " more tries.");
                                        failedTries++;
                                    }

                                    else
                                    {
                                        Authorised = true;
                                        writer.Write((byte)RemoteProtocol.ClientAuthorised);
                                        writer.Write("You have now been authenticated");
                                        RemoteLoginEventArgs e = new RemoteLoginEventArgs(Username,(IPEndPoint)rTcpClient.Client.RemoteEndPoint,rTcpClient);
                                        server.MinecraftBot.Events.RaiseUserLoggedIn(e);
                                    }
                                    break;

                                }

                            case RemoteProtocol.IncomingMessage:
                                {
                                    string chat = reader.ReadString();
                                    if(chat.StartsWith("&"))
                                    {
                                        string commandname = chat.TrimStart('&').Split(' ')[0];
                                        string args = String.Empty;
                                        try { args  = chat.Substring(commandname.Length + 2); } catch { }//Account for first white variable.
                                        args.TrimStart(' ');
                                        writer.Write((byte)RemoteProtocol.ServerResponse);

                                        switch(commandname)
                                        {
                                            case "commands":
                                                {
                                                    writer.Write((byte)0);
                                                    writer.Write("Commands: " +Environment.NewLine +
                                                                 "&commands - Returns a list of commands." + Environment.NewLine +
                                                                 "&players - Returns a list of players on the same map as the bot." + Environment.NewLine +
                                                                 "&listlogs - Returns a list of all log files in the bot directory." + Environment.NewLine +
                                                                 "&getlog - Gets the log file from the specified name.");
                                                    break;
                                                }

                                            case "players":
                                                {
                                                    writer.Write((byte)0);
                                                    Dictionary<byte, Player> players = server.MinecraftBot.Players;
                                                    List<string> Output = new List<string>();
                                                    foreach(Player player in players.Values)
                                                    {
                                                        Output.Add(player.Name);
                                                    }
                                                    string[] output = Output.ToArray();
                                                    writer.Write("Players in the current map: " +Environment.NewLine +
                                                                 string.Join(",",output));
                                                }
                                                break;

                                            case "listlogs":
                                                {
                                                    writer.Write((byte)0);
                                                    string[] rawFiles = Directory.GetFiles(Directory.GetCurrentDirectory());
                                                    List<String> Files = new List<string>(rawFiles);
                                                    System.Text.StringBuilder sb = new System.Text.StringBuilder();
                                                    foreach(string file in Files)
                                                    {
                                                        string fileRelative = Path.GetFileName(file);
                                                        if(fileRelative.StartsWith("log-")) sb.Append(fileRelative + Environment.NewLine);
                                                    }
                                                    writer.Write("Log files: " + Environment.NewLine + sb);
                                                    break;
                                                }

                                            case "getlog":
                                                {
                                                    string reqFile = Path.Combine(Directory.GetCurrentDirectory(),args);
                                                    string[] rawFiles = Directory.GetFiles(Directory.GetCurrentDirectory());
                                                    List<string> Files = new List<string>(rawFiles);
                                                    if(!Files.Contains(reqFile))
                                                    {
                                                        writer.Write((byte)0);
                                                        writer.Write("No file matching "+args + " found. You must include the extension as well.");
                                                    }
                                                    else
                                                    {
                                                        writer.Write((byte)1);
                                                        writer.Write(Path.GetFileName(reqFile));
                                                        writer.Write(File.ReadAllText(reqFile));
                                                    }
                                                    //writer.Write("Test.");

                                                    break;
                                                }

                                            default:
                                                {
                                                    writer.Write((byte)0);
                                                    writer.Write("Unknown command: " +chat.TrimStart('&').Split(' ')[0] + ". To see a list of commands, type &commands");
                                                    break;
                                                }
                                        }
                                        break;

                                    } //If the user wishes to do a server command.
                                    if(Authorised) //Only send if authorised, still read the message otherwise we become out of sync with the client.
                                    {
                                        Extensions.StripColors(chat);
                                        server.MinecraftBot.SendLongChat(chat);
                                    }
                                    break;
                                }
                            default:
                                throw new SocketException(-1);
                        }
                    }
                    catch
                    {
                        //A socket error has occured, don't log why.
                        break;
                    }

                    if (bytesRead == 0)
                    {
                        //The client has disconnected.
                        break;
                    }
                }
                SessionEndedEventArgs endede = new SessionEndedEventArgs(Username);
                server.MinecraftBot.Events.RaiseSessionEnded(endede);
                if(rTcpClient != null)
                {
                    rTcpClient.Client.Disconnect(true);
                    rTcpClient.Close();
                }
        }
Ejemplo n.º 2
0
        /// <summary> Loads configuration settings from a file called botsettings.txt </summary>
        private void LoadConfig()
        {
            try {
                config = new Config( "botsettings.txt" );
                if( !config.Exists() ) {
                    using( StreamWriter sw = new StreamWriter( "botsettings.txt" ) ) {
                        sw.WriteLine("UseRemoteServer: false");
                        sw.WriteLine("RemotePort: ");
                        sw.WriteLine("RemotePassword: "******"CommandsRequireOperator: true");
                        sw.WriteLine("ReconnectAfterKick: true");
                        sw.WriteLine("SaveMap: false");
                        sw.WriteLine("Operators:");
                        sw.WriteLine("#And now, a little explaination on what all these mean.");
                        sw.WriteLine("#UseRemoteServer - Allows remote clients to connect and perform actions on the bot / chat through it. By default, this is disabled." +
                                     "If you choose to use the remote function, you may need to forward the port and/or add an exception to your firewall.");
                        sw.WriteLine("#RemotePort - The port the server will listen on for remote clients. It is fine to leave this blank if UseRemoteServer is false.");
                        sw.WriteLine("#RemotePassword - The password to use for verifying remote clients. " +
                                     "If UseRemoteServer is true and this is blank, the password will be set to \"password\". ");
                        sw.WriteLine("#CommandsRequireOperators - This determines whether bot commands require the person who called them to be in the operators file." +
                                     "Usually you would want this to be true.");
                        sw.WriteLine("#ReconnectAfterKick - This determines if the bot will reconnect after being kicked. Note that if the bot receives a kick packet before" +
                                     "a ServerIdentification packet, it will abort, and assume it has been banned from connecting.");
                        sw.WriteLine("#SaveMap - This determines if the bot will save the map when the chunk packets are sent to it." +
                                     "If this is true, it will be saved as a fCraft compatible map. (Large maps of 512 x 512 x 512 " +
                                     "can use up to ~150 megabytes of RAM when saving, so be wary. After saving, memory usage should return to normal.");
                        sw.WriteLine( "#Operators: Comma separated list of operators, with no spaces. (e.g. test,test1,test2)" );
                        Events.RaiseConfigCreating( new ConfigCreatingEventArgs( config, sw ) );
                    }
                }

                config.Load();
                if( !config.TryParseValueOrDefault( "useremoteserver", false, out UseRemoteServer ) )
                    Log( LogType.Warning, "Couldn't load value for useremoteserver from config. Setting to default value of false" );
                if( UseRemoteServer ) {
                    int remotePort;
                    if( !config.TryParseValueOrDefault( "remoteport", 25561, out remotePort ) ) {
                        Log( LogType.Warning, "Couldn't load value for remoteport from config. Setting to default value of 25561" );
                    }
                    string remotePassword;
                    config.TryGetRawValue( "remotepassword", out remotePassword );
                    if( String.IsNullOrEmpty( remotePassword ) ) {
                        remotePassword = "******";
                        Log( LogType.Warning, "Couldn't load value for remotepassword from config. Setting to default value of \"password\"" );
                    }

                    server = new Server();
                    server.Start( this, remotePort, remotePassword );
                }

                if( !config.TryParseValueOrDefault( "commandsrequireoperator", true, out _requiresop ) )
                    Log( LogType.Warning, "Couldn't load value for commandsrequireoperator from config. Setting to default value of true" );
                if( !config.TryParseValueOrDefault( "reconnectafterkick", true, out _reconnectonkick ) )
                    Log( LogType.Warning, "Couldn't load value for reconnectafterkick from config. Setting to default value of true" );
                if( !config.TryParseValueOrDefault( "savemap", false, out _savemap ) )
                    Log( LogType.Warning, "Couldn't load value for savemap from config. Setting to default value of false" );
                string rawUsers; // Comma separated.
                config.TryGetRawValue( "operators", out rawUsers );
                if( String.IsNullOrEmpty( rawUsers ) ) {
                    Log( LogType.Warning, "Couldn't load value for operators from config. Setting to default value of empty." );
                } else {
                    string[] users = rawUsers.Split( ',' );
                    bool fixedNames = false;
                    for( int i = 0; i < users.Length; i++ ) {
                        if( users[i].IndexOf( ' ' ) != -1 ) {
                            fixedNames = true;
                            users[i] = users[i].Replace( " ", String.Empty );
                        }
                    }
                    if( fixedNames ) {
                        config.AddOrUpdateValue( "operators", String.Join( ",", users ) );
                        Log( LogType.BotActivity, "Fixed up spaces in the list of operators." );
                        config.Save();
                    }
                    Users.AddRange( users );
                }

                Events.RaiseConfigLoading( new ConfigLoadingEventArgs( config ) );
            } catch( Exception e ) {
                Log( LogType.Error, "Couldn't load config:", e.ToString() );
            }
        }