Windows system >> Windowsの知識 >  >> コンピュータソフトウェアのチュートリアル >> サーバー技術 >> サーバーについて >> ケースの共有:Fantasy Westward Journey Server最適化

ケースの共有:Fantasy Westward Journey Server最適化

  

歴史的エンジニアリングへのパッチ適用は面倒です。

最初の2日間は、Fantasy Westward Journeyサーバーの最適化について説明しています。私は最近広州に滞在しました、そして私はこの問題に特化した一週間を過ごすことを計画しています。私は以前オンラインチャットをしていたので、一緒に座っている場合にのみ問題を本当に理解することができます。

現在、Fantasy Westward Journeyは単一のマシンのみを使用し、最大8個のCPUと8Gのメモリを搭載しています。最も活気のあるサーバーでさえ、これらのリソースを使用することはできません(約3 CPUとメモリの半分)。コアプログラムはほぼ10年前に書かれました、そしてそれはWestward JourneyからWestまで続きます。私は過去2年間無料の昼食を楽しんできましたが、ハードウェア構成のアップグレードにより、単一サーバーのオンライン容量は12,000になりました。サーバーの応答速度を調べたグラフによると、現在の問題は定期的に応答が遅いということです。定期的に、サーバーの応答時間は1000ミリ秒を超えます。その理由は、その時点でディスクIOが非常に混雑していたためです。定期的にプレーヤーデータを保存するサービスのIO使用、およびSAがデータの定期的なバックアップを作成するスクリプトは、多くのIO時間を消費します。やがてマシンは過負荷になりました。

IOの過負荷が最終的にゲームサービスのパフォーマンスにどのように影響するかは、徹底的な議論ではありません。私は過去2日間のシステム構造を主に分析し、改善計画について考えました。

実際、古いシステムは複雑ではなく、コード量もかなり少ないです。関連するサービスコードは、ほんの数千行のクリーンなCコードです。何百万ものユーザーと請求プロセスが関係しているので、これを動かす人はいません。デザインが良いか悪いかにかかわらず、達成された性能は問題があり安定性への道を与えます。すべての種類の苦情によって引き起こされる「歴史的な理由」は、再設計されたとしても、確かに書かれていない場合、チャット中にのみ不平を言うことができます。過去2年間で、私はこの問題のリファクタリングにますます無関心になってきましたが、なぜそうしないのか、そうでないのですか?もっと多くの場合、それはプログラマーの昼食だけです。各システムが書かれると、それは後悔でいっぱいです。それがうまくいけば、最大の可能性はそれが使用され続けるということです。次回は新しいアイデアをすべて残してください。

長年にわたって安定して稼働してきた古いシステムにとって、それを変換するための良い方法を見つけることはほとんど意味がありません。最も重要なことは、最小限の影響で既存のシステムに何かを追加してパフォーマンスを向上させる方法です。モジュール間の明確な分割は非常に重要です。サービスの独立性も必要です。実行中のデータサービスと請求およびユーザ認証サービスをサービスプログラムに入れることは大きな間違いです。データを削除するのは非常に困難です。

データサービスはC /S構造を使用しています。しかし、データベースを使用する代わりに、ローカルファイルシステムが直接使用されます。全体的な設計は優れていますが、データサービス自体のメカニズムは非常に悪いです。共有メモリは、IPCのパフォーマンスを向上させるためにCとSの間でデータを交換するために使用されます。ゲームのメインプロセスであるCは1つだけです。また、Sは複数存在する可能性があります。サービスは同時に提供できます。共有メモリとデータを交換するために、複数のSとCの間でコマンドをパイプライン化します。意図はありますが、プロトコル設計には問題があります。 Cはデータ域を直接操作し、固有性があるので、結果はSではなくCにデータ域のブロック管理を配置するように設計されています。

たとえば、ゲームプロセス(C)がユーザーのデータを読み込む必要がある場合は、まずデータ領域内のスペースを探し、次にユーザーのデータを指定されたデータの場所に読み込むようにSに指示します。データ域のクリーニングもCによって行われます。一時的に使用されていないキャッシュデータ(オフラインのプレーヤーなど)が必要な場合は、Sがデータ領域に対して直接キャッシュを実行することは不可能です。あるいは、別のキャッシュサービスを追加します(これには2倍のメモリとメモリのコピー操作が必要です)実装では、複数のSが同時にCを処理する必要があると考えています。悪い

結果として、データサービス全体(読み書きを問わず)はキャッシュフリーになります。キャッシュはそれをするためにOSだけに頼ります。それが1桁低いときには、これは問題になりません。しかし、オンラインユーザー数が10,000人に達した後、問題が明らかになりました。結局のところ、最終的な需要に合わせてカスタマイズを増やすほど、ハードウェアを最大限に活用することができます。

以下は私が実装したメモリ/鍵データベースの設計の記録です。

数日前に差分を保存するという戦略を実現するには、差分情報を保存するという戦略(測定されたIO操作を90%減らすことができる)だけで、まずデータの読み書きサービスの場所を統一する必要があります。データ交換をローカルファイルシステムに頼ることはできません。私は以前にRedisのようないくつかのインメモリデータベースを調べ、そしてついに自分自身を実装することにしました。私はすでに要件をよく知っているので、ハードウェアの能力を最大限に引き出すためにアルゴリズムを高度にカスタマイズすることができます。コード量は多すぎません。 (500行のCコードで制御され、最終的には300行のCプログラムが書き留められます)

私たちの要求はこれです:サービスプログラムは週に一度停止するでしょう。 1週間に関わるプレーヤーデータの総数は100,000です。各データセットは4Kから32Kの間です。すべてテキストデータです。データ文字列のキー/値データストレージサービスへのIDと見なすことができます。全データはメモリに入れることができると推定される。データは頻繁に更新され、更新後に長さが変わります。

このk /vメモリデータサービスの実装に1日を費やしました。効率性とコード実装の単純さを確保しながら、メモリの使用を最大化するため。メモリを1Kのブロックにカットするために、メモリのブロック全体を事前に割り当てる方式を使用しました。そして、単独でリンクされたリストを使って一緒に文字列を作るメモリキャッシュのヒット効率を考慮してください。リンクリストポインタ自体はデータ記憶領域とは別のものです。 (ほとんどの場合、特定のデータにアクセスしなくてもリンクリストポインタにアクセスするだけです。)

リンクリストポインタは、メモリアドレスではなくシリアル番号を使用します。これにより、4バイトのインデックス(64ビットシステムでも最大4Tのデータを管理するために使用できます)を使用できます。一重リンクリストは、二重リンクリストに比べて、ポインタ操作の半分を節約し、少量のメモリを節約できます。その代償は、コードを書くのがもう少し複雑だということです。

すべてのメモリブロックは、フリーブロックと使用済みブロックの2つの部分に分けられます。初めはすべてのスペースは無料です。データが内部に配置されると、フリーリストから十分なブロックが取り出され、使用済みリストの最後に配置されます。キャッシュスペースが一杯になると、使用済みブロックリストのヘッダーから一部のスペースが削除され、スペースブロックに戻されます(データエリアは長期間アクセスされません)。データを読むたびに、それが使用済みリストの最後に調整されて、データが最終的にクリーンアップされるようにします。

さらに、ハッシュテーブルはidからキャッシュ内のブロックセグメントのヘッダーにマッピングされます(これは単一リンクリストなので、前のノードは実装に保存する必要があります)。このように、O(1)時間を使用して、指定されたIDに対応するデータ領域を照会できます。キャッシュに格納されたデータは、アドレスで完全に連続している必要はありません。ディスクとは異なり、メモリはランダムアクセス性能とシーケンシャルアクセス性能が劣ります。これは、メモリ空間の利用効率に有利です。
zh-CN"],null,[1],zh-TW"]]]

Copyright © Windowsの知識 All Rights Reserved