QueryServer.pm
上传用户:market2
上传日期:2018-11-18
资源大小:18786k
文件大小:3k
源码类别:

外挂编程

开发平台:

Windows_Unix

  1. ###########################################################
  2. # Poseidon server - OpenKore communication channel
  3. #
  4. # This program is free software; you can redistribute it and/or 
  5. # modify it under the terms of the GNU General Public License 
  6. # as published by the Free Software Foundation; either version 2 
  7. # of the License, or (at your option) any later version.
  8. #
  9. # Copyright (c) 2005-2006 OpenKore Development Team
  10. ###########################################################
  11. package Poseidon::QueryServer;
  12. use strict;
  13. use Scalar::Util;
  14. use Base::Server;
  15. use Bus::MessageParser;
  16. use Bus::Messages qw(serialize);
  17. use Poseidon::RagnarokServer;
  18. use base qw(Base::Server);
  19. use Plugins;
  20. my $CLASS = "Poseidon::QueryServer";
  21. # struct Request {
  22. #     Bytes packet;
  23. #     Base::Server::Client client;
  24. # }
  25. ##
  26. # Poseidon::QueryServer->new(String port, String host, Poseidon::RagnarokServer ROServer)
  27. # port: The port to start this server on.
  28. # host: The host to bind this server to.
  29. # ROServer: The RagnarokServer object to send GameGuard queries to.
  30. # Require: defined($port) && defined($ROServer)
  31. #
  32. # Create a new Poseidon::QueryServer object.
  33. sub new {
  34. my ($class, $port, $host, $roServer) = @_;
  35. my $self = $class->SUPER::new($port, $host);
  36. # Invariant: server isa 'Poseidon::RagnarokServer'
  37. $self->{"$CLASS server"} = $roServer;
  38. # Array<Request> queue
  39. #
  40. # The GameGuard query packets queue.
  41. #
  42. # Invariant: defined(queue)
  43. $self->{"$CLASS queue"} = [];
  44. return $self;
  45. }
  46. ##
  47. # void $QueryServer->process(Base::Server::Client client, String ID, Hash* args)
  48. #
  49. # Push an OpenKore GameGuard query to the queue.
  50. sub process {
  51. my ($self, $client, $ID, $args) = @_;
  52. if ($ID ne "Poseidon Query") {
  53. $client->close();
  54. return;
  55. }
  56. print "Received query from client " . $client->getIndex() . "n";
  57. my %request = (
  58. packet => $args->{packet},
  59. client => $client
  60. );
  61. # perform client authentication here
  62. Plugins::callHook('Poseidon/server_authenticate', {
  63. args_hash => $args,
  64. });
  65. # note: the authentication plugin must set auth_failed to true if it doesn't
  66. # want the Poseidon server to respond to the query
  67. return if ($args->{auth_failed});
  68. Scalar::Util::weaken($request{client});
  69. push @{$self->{"$CLASS queue"}}, %request;
  70. # my $packet = substr($ipcArgs->{packet}, 0, 18);
  71. }
  72. ##################################################
  73. sub onClientNew {
  74. my ($self, $client) = @_;
  75. $client->{"$CLASS parser"} = new Bus::MessageParser();
  76. }
  77. sub onClientData {
  78. my ($self, $client, $msg) = @_;
  79. my ($ID, $args);
  80. my $parser = $client->{"$CLASS parser"};
  81. $parser->add($msg);
  82. while ($args = $parser->readNext($ID)) {
  83. $self->process($client, $ID, $args);
  84. }
  85. }
  86. sub iterate {
  87. my ($self) = @_;
  88. my ($server, $queue);
  89. $self->SUPER::iterate();
  90. $server = $self->{"$CLASS server"};
  91. $queue = $self->{"$CLASS queue"};
  92. if ($server->getState() eq 'requested') {
  93. # Send the response to the client.
  94. if (@{$queue} > 0 && $queue->[0]{client}) {
  95. my ($data, %args);
  96. $args{packet} = $server->readResponse();
  97. $data = serialize("Poseidon Reply", %args);
  98. $queue->[0]{client}->send($data);
  99. $queue->[0]{client}->close();
  100. print "Sent result to client " . $queue->[0]{client}->getIndex() . "n";
  101. }
  102. shift @{$queue};
  103. } elsif (@{$queue} > 0 && $server->getState() eq 'ready') {
  104. print "Querying Ragnarok Online client.n";
  105. $server->query($queue->[0]{packet});
  106. }
  107. }
  108. 1;