如下是最近某個項目的一次經歷,最終並無按照這樣的方案來優化,但對思路確實是一個提升,因此記錄在此。mysql
-------------------------------------------------------------------------------------------------------------------sql
項目D爲單機服務器,聽說在線達到1500後,會很卡,因而想仔細分析了其中的緣由。數據庫
總體來講:C++服務器+mysql數據庫,多線程。可是是單服。服務器
請教了前同事,在他的一步步詢問下,理清了服務器的當前架構。網絡
同事指導,對於服務器性能分析,要從內存分配和多線程兩個方面入手。session
修改內存分配策略不但能下降內存,還能減小碎片,最終勢必會提升遊戲性能(分配阻塞致使性能低)。多線程
使用多線程,將複雜的邏輯異步到不一樣的線程去計算,減小了主邏輯的等待,也必然提升了流暢性。架構
線程方面:異步
1 一個socket負責監聽全部客戶端的session。使用了完成端口的概念,起了3個線程,負責收消息,收到後,將消息放入一個全局的隊列revQueue中,這個隊列包含全部玩家的全部消息。socket
2 全局的session管理類,管理全部客戶端的session。每一個玩家發送消息時,寫入本身的發消息隊列ownSendQueue中。
3 一個單獨的數據庫操做隊列dbQueue,負責全部對數據庫的讀取。
4 啓動遊戲時,開了一個線程,專門負責內部邏輯的刷新。包括各類timer,數據庫隊列dbQueue的分發,全局收消息隊列revQueue的分發(每次輪詢到時,會將隊列中的全部消息都分發出去),每一個session的發消息隊列ownSendQueue,其它遊戲內的各類update(血量體力等各類恢復)。
內存分配:
1 會頻繁使用到標準庫的map,vector,string對象。
2 對自定義的類,有內存池的管理策略。當前策略:
再來看下服務器當前的配置,在線人比較多的一個區服務器,包括三組服務器:
32G內存+10個CPU,每組在線約300人。cpu使用7%左右,內存使用17%左右。
這一系列的分析出來,問題相對而言就明顯了。
內存沒有達到有效的使用。
邏輯全在一個線程,應該就是整個瓶頸所在了。
針對問題提出的優化策略:
1.內存分配方法
對於已有的內存池策略:
完全的接管內存分配
初步測試,接入tcmalloc後,內存佔用由原來的107448降爲67108,提升大約40%,可驗證對在線的影響。
2.並行計算
以上是在不改變當前單服的狀態下,可作出的優化。畢竟單服總有上限,若是以上的優化都不能達到想要的效果,就要拆分服務器了。
增長LoginServer
Gate和Master之間增長LoginServer,或者Gate自己增長LoginServer的功能。
負責:登錄驗證、創角、角色列表、刪角、 封禁IP過濾等處理,其它邏輯交給Master。
增長LogServer,監聽Master傳送的消息,專門負責和logDB的交互。
上述修改完成後,若是在線依然沒法知足,可根據統計數據,逐步拆分出GameGate,GMGate,ChatServer,TaskServer,DBServer。
-------------------------------------------------------------------------------------------------------------------
再次重複下,以上只是某個項目的一次經歷,最終並無按照這樣的方案來優化,但對思路確實是一個提升,因此記錄在此。