This file is indexed.

/usr/include/gnelib/EventThread.h is in libgnelib-dev 0.75+svn20091130-1.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
#ifndef _EVENTTHREAD_H_
#define _EVENTTHREAD_H_

/* GNE - Game Networking Engine, a portable multithreaded networking library.
 * Copyright (C) 2001-2006 Jason Winnebeck 
 * Project website: http://www.gillius.org/gne/
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */

#include <gnelib/Thread.h>
#include <gnelib/Error.h>
#include <gnelib/Mutex.h>
#include <gnelib/ConditionVariable.h>
#include <gnelib/Time.h>
#include <gnelib/SmartPtr.h>
#include <gnelib/WeakPtr.h>

namespace GNE {
class ConnectionListener;
class Connection;

/**
 * @ingroup internal
 *
 * Internal class used by GNE to manage Connection events.
 *
 * Each Connection has an EventThread.  This is used internally by the
 * Connection class to act as a proxy to dispatch events to the
 * ConnectionListener.  Because of this, only one event per Connection will
 * be active at any one time.  Another appropriate name that might describe
 * this would be an EventQueue.  But to improve efficency and stability,
 * some events may be reordered or combined.  Remember that onReceive means 1
 * or more packets have been received.  If multiple onReceive or
 * onDoneWriting occur, they will probably be combined.  Error events will
 * always have first priority, and if the error leads to a disconnect,
 * pending events after that will not be called (except for onDisconnect).
 *
 * EventThread was created to solve several things:
 * <ul>
 * <li>Complexities due to multiple threads calling the ConnectionListener at
 *   the same time.</li>
 * <li>Serialized events and all events executing in the same thread is easy
 *   to control and eliminates lots of previous ways for syncronization errors
 *   to creep in.</li>
 * <li>Events taking a while to execute or block (although this is an error),
 *   won't stop the rest of GNE from functioning, but will only stop a single
 *   Connection.</li>
 * <li>Multiple event threads take better advantage of multiprocessor
 *   machines.</li>
 * </ul>
 */
class EventThread : public Thread {
protected:
  /**
   * @see create
   */
  EventThread( const SmartPtr<Connection>& conn );

public:
  typedef SmartPtr<EventThread> sptr;
  typedef WeakPtr<EventThread> wptr;

  /**
   * Initializes this class as a event thread for a listener.
   * The conn pointer is used to call disconnect when an onFailure
   * event is finally processed.  This is to assure that disconnect is called
   * from a safe thread that won't lead to deadlock when a failure occurs.
   *
   * The SmartPtr also keeps the Connection alive if it is still active.
   */
  static sptr create( const SmartPtr<Connection>& conn );

  virtual ~EventThread();

  /**
   * Use GNE::Connection::getListener.
   */
  SmartPtr<ConnectionListener> getListener() const;
  
  /**
   * Use GNE::Connection::setListener.
   */
  void setListener( const SmartPtr<ConnectionListener>& listener );

  /**
   * Use GNE::Connection::getTimeout.
   */
  int getTimeout() const;

  /**
   * Use GNE::Connection::setTimeout.
   */
  void setTimeout(int ms);

  /**
   * For more information about these events, see ConnectionListener.  The
   * processing of an onDisconnect event will be the last, and the thread
   * will essentially stop when onDisconnect completes.
   */
  void onDisconnect();

  /**
   * For more information about these events, see ConnectionListener.
   */
  void onExit();

  /**
   * For more information about these events, see ConnectionListener.
   */
  void onFailure(const Error& error);

  /**
   * For more information about these events, see ConnectionListener.
   */
  void onError(const Error& error);

  /**
   * For more information about these events, see ConnectionListener.
   */
  void onReceive();

  /**
   * Overrides Thread::shutDown so that the daemon thread will
   * be woken up since it might be waiting on a ConditionVariable.  Once it
   * shuts down it should not be activated again.
   */
  void shutDown();

protected:
  /**
   * This thread serializes events for a Connection.
   */
  void run();

private:
  /**
   * Checks for timeout, triggering an onTimeout event and handling the time
   * variables, if needed.
   */
  void checkForTimeout();

  /**
   * Resets the timeout counter by making nextTimeout be the current absolute
   * time + the timeout interval.
   */
  void resetTimeout();

  void onTimeout();

  //See the ctor for more information about ourConn.
  SmartPtr<Connection> ourConn;

  //The listener for our events.  All on* events go here.  This is protected
  //so ClientConnection can send events as well.
  SmartPtr<ConnectionListener> eventListener;

  ConditionVariable eventSync;

  mutable ConditionVariable listenSync;

  //Variables for handling onTimeout events.
  Mutex timeSync;
  Time timeout;
  Time nextTimeout;

  volatile bool onReceiveEvent;
  volatile bool onTimeoutEvent;

  //If this is true, we should not receive any more events.  It should be the
  //next event called, and everything else should stop.
  volatile bool onDisconnectEvent;

  //If this is true, an graceful exit notice was received, and the next event
  //is an onDisconnectEvent.
  volatile bool onExitEvent;

  //Wish we could combine error events and report the last error, but this
  //really isn't what the API specifies, so we should keep track of every
  //error.
  std::queue<Error*> eventQueue;

  //If this is true, we have a onFailure event which takes precedence over
  //everything.
  Error* failure;
};

}
#endif /* _EVENTTHREAD_H_ */