Better packing for clients
authoralfadur
Fri, 13 Jul 2018 19:52:19 +0300
changeset 13525 1ee192f13456
parent 13490 c85b324c4c2d
child 13526 ba5211dddb21
Better packing for clients
gameServer2/src/protocol/messages.rs
gameServer2/src/protocol/parser.rs
gameServer2/src/protocol/test.rs
gameServer2/src/server/actions.rs
gameServer2/src/server/client.rs
gameServer2/src/server/handlers/inroom.rs
gameServer2/src/server/room.rs
gameServer2/src/server/server.rs
--- a/gameServer2/src/protocol/messages.rs	Thu Jul 12 14:46:16 2018 +0200
+++ b/gameServer2/src/protocol/messages.rs	Fri Jul 13 19:52:19 2018 +0300
@@ -18,7 +18,7 @@
     Info(String),
     // not entered state
     Nick(String),
-    Proto(u32),
+    Proto(u16),
     Password(String, String),
     Checker(u32, String, String),
     // lobby
@@ -76,7 +76,7 @@
     Pong,
     Bye(String),
     Nick(String),
-    Proto(u32),
+    Proto(u16),
     LobbyLeft(String, String),
     LobbyJoined(Vec<String>),
     ChatMsg {nick: String, msg: String},
--- a/gameServer2/src/protocol/parser.rs	Thu Jul 12 14:46:16 2018 +0200
+++ b/gameServer2/src/protocol/parser.rs	Fri Jul 13 19:52:19 2018 +0300
@@ -25,6 +25,7 @@
 named!(str_line<&[u8],   &str>, map_res!(not_line_ending, str::from_utf8));
 named!(  a_line<&[u8], String>, map!(str_line, String::from));
 named!( u8_line<&[u8],     u8>, map_res!(str_line, FromStr::from_str));
+named!(u16_line<&[u8],    u16>, map_res!(str_line, FromStr::from_str));
 named!(u32_line<&[u8],    u32>, map_res!(str_line, FromStr::from_str));
 named!(yes_no_line<&[u8], bool>, alt!(
       do_parse!(tag_no_case!("YES") >> (true))
@@ -87,7 +88,7 @@
     | do_parse!(tag!("ROOM_NAME")   >> eol >> n: a_line >> (RoomName(n)))
     | do_parse!(tag!("REMOVE_TEAM") >> eol >> n: a_line >> (RemoveTeam(n)))
 
-    | do_parse!(tag!("PROTO")   >> eol >> d: u32_line >> (Proto(d)))
+    | do_parse!(tag!("PROTO")   >> eol >> d: u16_line >> (Proto(d)))
 
     | do_parse!(tag!("QUIT")   >> msg: opt_param >> (Quit(msg)))
 ));
--- a/gameServer2/src/protocol/test.rs	Thu Jul 12 14:46:16 2018 +0200
+++ b/gameServer2/src/protocol/test.rs	Fri Jul 13 19:52:19 2018 +0300
@@ -118,7 +118,7 @@
         7 => SuperPower(),
         8 => Info(Ascii),
         9 => Nick(Ascii),
-        10 => Proto(u32),
+        10 => Proto(u16),
         11 => Password(Ascii, Ascii),
         12 => Checker(u32, Ascii, Ascii),
         13 => List(),
--- a/gameServer2/src/server/actions.rs	Thu Jul 12 14:46:16 2018 +0200
+++ b/gameServer2/src/server/actions.rs	Fri Jul 13 19:52:19 2018 +0300
@@ -5,7 +5,7 @@
 };
 use super::{
     server::HWServer,
-    room::{GameInfo},
+    room::GameInfo,
     client::HWClient,
     coretypes::{ClientId, RoomId, GameCfg, VoteType},
     room::HWRoom,
@@ -25,7 +25,7 @@
     ToSelf,
     ToAll {
         room_id: Option<RoomId>,
-        protocol: Option<u32>,
+        protocol: Option<u16>,
         skip_self: bool
     }
 }
@@ -60,7 +60,7 @@
         self
     }
 
-    pub fn with_protocol(mut self, protocol_number: u32) -> PendingMessage {
+    pub fn with_protocol(mut self, protocol_number: u16) -> PendingMessage {
         if let Destination::ToAll {ref mut protocol, ..} = self.destination {
             *protocol = Some(protocol_number)
         }
@@ -218,14 +218,14 @@
                 let c = &mut server.clients[client_id];
                 r.players_number += 1;
                 c.room_id = Some(room_id);
-                c.is_joined_mid_game = false;
-                if r.master_id == Some(c.id) {
+
+                let is_master = r.master_id == Some(c.id);
+                c.set_is_master(is_master);
+                c.set_is_ready(is_master);
+                c.set_is_joined_mid_game(false);
+
+                if is_master {
                     r.ready_players_number += 1;
-                    c.is_master = true;
-                    c.is_ready = true;
-                } else {
-                    c.is_ready = false;
-                    c.is_master = false;
                 }
 
                 let mut v = vec![
@@ -236,11 +236,11 @@
                     v.push(ChatMsg {nick: "[greeting]".to_string(), msg: r.greeting.clone()}
                         .send_self().action());
                 }
-                if !c.is_master {
+                if !c.is_master() {
                     let team_names: Vec<_>;
                     if let Some(ref mut info) = r.game_info {
-                        c.is_in_game = true;
-                        c.is_joined_mid_game = true;
+                        c.set_is_in_game(true);
+                        c.set_is_joined_mid_game(true);
 
                         {
                             let teams = info.client_teams(c.id);
@@ -319,7 +319,7 @@
                             .send(to).action());
                     }
                     let nicks: Vec<_> = server.clients.iter()
-                        .filter(|(_, c)| c.room_id == Some(r.id) && c.is_ready)
+                        .filter(|(_, c)| c.room_id == Some(r.id) && c.is_ready())
                         .map(|(_, c)| c.nick.clone()).collect();
                     if !nicks.is_empty() {
                         actions.push(ClientFlags("+r".to_string(), nicks)
@@ -411,10 +411,10 @@
             let lobby_id = server.lobby_id;
             if let (c, Some(r)) = server.client_and_room(client_id) {
                 r.players_number -= 1;
-                if c.is_ready && r.ready_players_number > 0 {
+                if c.is_ready() && r.ready_players_number > 0 {
                     r.ready_players_number -= 1;
                 }
-                if c.is_master && (r.players_number > 0 || r.is_fixed) {
+                if c.is_master() && (r.players_number > 0 || r.is_fixed) {
                     actions.push(ChangeMaster(r.id, None));
                 }
                 actions.push(ClientFlags("-i".to_string(), vec![c.nick.clone()])
@@ -450,7 +450,7 @@
             if let (c, Some(r)) = server.client_and_room(client_id) {
                 match r.master_id {
                     Some(id) if id == c.id => {
-                        c.is_master = false;
+                        c.set_is_master(false);
                         r.master_id = None;
                         actions.push(ClientFlags("-h".to_string(), vec![c.nick.clone()])
                             .send_all().in_room(r.id).action());
@@ -464,7 +464,7 @@
                         .send_all().in_room(r.id).action());
                 }
             }
-            new_id.map(|id| server.clients[id].is_master = true);
+            new_id.map(|id| server.clients[id].set_is_master(true));
             server.react(client_id, actions);
         }
         RemoveTeam(name) => {
@@ -476,7 +476,7 @@
                 }
                 actions.push(TeamRemove(name.clone()).send_all().in_room(r.id).action());
                 actions.push(SendRoomUpdate(None));
-                if r.game_info.is_some() && c.is_in_game {
+                if r.game_info.is_some() && c.is_in_game() {
                     actions.push(SendTeamRemovalMessage(name));
                 }
             }
@@ -514,7 +514,7 @@
                     room.start_round();
                     for id in room_clients {
                         let c = &mut server.clients[id];
-                        c.is_in_game = true;
+                        c.set_is_in_game(false);
                         c.team_indices = room.client_team_indices(c.id);
                     }
                     vec![RunGame.send_all().in_room(room.id).action(),
@@ -564,7 +564,7 @@
 
             if let Some(info) = old_info {
                 for (_, c) in server.clients.iter() {
-                    if c.room_id == Some(room_id) && c.is_joined_mid_game {
+                    if c.room_id == Some(room_id) && c.is_joined_mid_game() {
                         actions.push(SendRoomData{
                             to: c.id, teams: false,
                             config: true, flags: false});
@@ -579,10 +579,11 @@
             let nicks: Vec<_> = server.clients.iter_mut()
                 .filter(|(_, c)| c.room_id == Some(room_id))
                 .map(|(_, c)| {
-                    c.is_ready = c.is_master;
-                    c.is_joined_mid_game = false;
+                    let is_master = c.is_master();
+                    c.set_is_ready(is_master);
+                    c.set_is_joined_mid_game(false);
                     c
-                }).filter_map(|c| if !c.is_master {
+                }).filter_map(|c| if !c.is_master() {
                     Some(c.nick.clone())
                 } else {
                     None
--- a/gameServer2/src/server/client.rs	Thu Jul 12 14:46:16 2018 +0200
+++ b/gameServer2/src/server/client.rs	Fri Jul 13 19:52:19 2018 +0300
@@ -1,18 +1,20 @@
 use super::coretypes::ClientId;
 
+const IS_ADMIN: u8 = 0b0000_0001;
+const IS_MASTER: u8 = 0b0000_0010;
+const IS_READY: u8 = 0b0000_0100;
+const IS_IN_GAME: u8 = 0b0000_1000;
+const IS_JOINED_MID_GAME: u8 = 0b0001_0000;
+
 pub struct HWClient {
     pub id: ClientId,
     pub room_id: Option<usize>,
     pub nick: String,
-    pub protocol_number: u32,
-    pub is_admin: bool,
-    pub is_master: bool,
-    pub is_ready: bool,
-    pub is_in_game: bool,
+    pub protocol_number: u16,
+    flags: u8,
     pub teams_in_game: u8,
     pub team_indices: Vec<u8>,
-    pub clan: Option<u8>,
-    pub is_joined_mid_game: bool,
+    pub clan: Option<u8>
 }
 
 impl HWClient {
@@ -22,14 +24,26 @@
             room_id: None,
             nick: String::new(),
             protocol_number: 0,
-            is_admin: false,
-            is_master: false,
-            is_ready: false,
-            is_in_game: false,
+            flags: 0,
             teams_in_game: 0,
             team_indices: Vec::new(),
             clan: None,
-            is_joined_mid_game: false,
         }
     }
+
+    fn set(&mut self, mask: u8, value: bool) {
+        if value { self.flags |= mask } else { self.flags &= !mask }
+    }
+
+    pub fn is_admin(&self)-> bool { self.flags & IS_ADMIN != 0 }
+    pub fn is_master(&self)-> bool { self.flags & IS_MASTER != 0 }
+    pub fn is_ready(&self)-> bool { self.flags & IS_READY != 0 }
+    pub fn is_in_game(&self)-> bool { self.flags & IS_IN_GAME != 0 }
+    pub fn is_joined_mid_game(&self)-> bool { self.flags & IS_JOINED_MID_GAME != 0 }
+
+    pub fn set_is_admin(&mut self, value: bool) { self.set(IS_ADMIN, value) }
+    pub fn set_is_master(&mut self, value: bool) { self.set(IS_MASTER, value) }
+    pub fn set_is_ready(&mut self, value: bool) { self.set(IS_READY, value) }
+    pub fn set_is_in_game(&mut self, value: bool) { self.set(IS_IN_GAME, value) }
+    pub fn set_is_joined_mid_game(&mut self, value: bool) { self.set(IS_JOINED_MID_GAME, value) }
 }
\ No newline at end of file
--- a/gameServer2/src/server/handlers/inroom.rs	Thu Jul 12 14:46:16 2018 +0200
+++ b/gameServer2/src/server/handlers/inroom.rs	Fri Jul 13 19:52:19 2018 +0300
@@ -102,17 +102,17 @@
         },
         Fix => {
             if let (c, Some(r)) = server.client_and_room(client_id) {
-                if c.is_admin { r.is_fixed = true }
+                if c.is_admin() { r.is_fixed = true }
             }
         }
         Unfix => {
             if let (c, Some(r)) = server.client_and_room(client_id) {
-                if c.is_admin { r.is_fixed = false }
+                if c.is_admin() { r.is_fixed = false }
             }
         }
         Greeting(text) => {
             if let (c, Some(r)) = server.client_and_room(client_id) {
-                if c.is_admin || c.is_master && !r.is_fixed {
+                if c.is_admin() || c.is_master() && !r.is_fixed {
                     r.greeting = text
                 }
             }
@@ -138,14 +138,15 @@
         },
         ToggleReady => {
             let actions = if let (c, Some(r)) = server.client_and_room(client_id) {
-                let flags = if c.is_ready {
+                let flags = if c.is_ready() {
                     r.ready_players_number -= 1;
                     "-r"
                 } else {
                     r.ready_players_number += 1;
                     "+r"
                 };
-                c.is_ready = !c.is_ready;
+                let is_ready = !c.is_ready();
+                c.set_is_ready(is_ready);
                 let mut v =
                     vec![ClientFlags(flags.to_string(), vec![c.nick.clone()])
                         .send_all().in_room(r.id).action()];
@@ -209,7 +210,7 @@
                 let room_id = r.id;
                 let addable_hedgehogs = r.addable_hedgehogs();
                 if let Some((_, mut team)) = r.find_team_and_owner_mut(|t| t.name == team_name) {
-                    if !c.is_master {
+                    if !c.is_master() {
                         vec![ProtocolError("You're not the room master!".to_string())]
                     } else if number < 1 || number > 8
                            || number > addable_hedgehogs + team.hedgehogs_number {
@@ -233,7 +234,7 @@
             let actions = if let (c, Some(r)) = server.client_and_room(client_id) {
                 let room_id = r.id;
                 if let Some((owner, mut team)) = r.find_team_and_owner_mut(|t| t.name == team_name) {
-                    if !c.is_master {
+                    if !c.is_master() {
                         vec![ProtocolError("You're not the room master!".to_string())]
                     } else if false  {
                         Vec::new()
@@ -260,7 +261,7 @@
             let actions = if let (c, Some(r)) = server.client_and_room(client_id) {
                 if r.is_fixed {
                     vec![Warn("Access denied.".to_string())]
-                } else if !c.is_master {
+                } else if !c.is_master() {
                     vec![ProtocolError("You're not the room master!".to_string())]
                 } else {
                     let v = vec![cfg.to_server_msg()
@@ -337,7 +338,7 @@
         }
         ForceVote(vote) => {
             let actions = if let (c, Some(r)) = server.client_and_room(client_id) {
-                vec![AddVote{ vote, is_forced: c.is_admin} ]
+                vec![AddVote{ vote, is_forced: c.is_admin()} ]
             } else {
                 Vec::new()
             };
@@ -383,8 +384,8 @@
         RoundFinished => {
             let mut actions = Vec::new();
             if let (c, Some(r)) = server.client_and_room(client_id) {
-                if c.is_in_game {
-                    c.is_in_game = false;
+                if c.is_in_game() {
+                    c.set_is_in_game(false);
                     actions.push(ClientFlags("-g".to_string(), vec![c.nick.clone()]).
                         send_all().in_room(r.id).action());
                     if r.game_info.is_some() {
--- a/gameServer2/src/server/room.rs	Thu Jul 12 14:46:16 2018 +0200
+++ b/gameServer2/src/server/room.rs	Fri Jul 13 19:52:19 2018 +0300
@@ -111,7 +111,7 @@
     pub master_id: Option<ClientId>,
     pub name: String,
     pub password: Option<String>,
-    pub protocol_number: u32,
+    pub protocol_number: u16,
     pub greeting: String,
     pub is_fixed: bool,
 
--- a/gameServer2/src/server/server.rs	Thu Jul 12 14:46:16 2018 +0200
+++ b/gameServer2/src/server/server.rs	Fri Jul 13 19:52:19 2018 +0300
@@ -124,7 +124,7 @@
         self.select_clients(|(_, c)| c.room_id == Some(room_id))
     }
 
-    pub fn protocol_clients(&self, protocol: u32) -> Vec<ClientId> {
+    pub fn protocol_clients(&self, protocol: u16) -> Vec<ClientId> {
         self.select_clients(|(_, c)| c.protocol_number == protocol)
     }