IPXMGR.H (19867B)
1 // 2 // Copyright 2020 Electronic Arts Inc. 3 // 4 // TiberianDawn.DLL and RedAlert.dll and corresponding source code is free 5 // software: you can redistribute it and/or modify it under the terms of 6 // the GNU General Public License as published by the Free Software Foundation, 7 // either version 3 of the License, or (at your option) any later version. 8 9 // TiberianDawn.DLL and RedAlert.dll and corresponding source code is distributed 10 // in the hope that it will be useful, but with permitted additional restrictions 11 // under Section 7 of the GPL. See the GNU General Public License in LICENSE.TXT 12 // distributed with this program. You should have received a copy of the 13 // GNU General Public License along with permitted additional restrictions 14 // with this program. If not, see https://github.com/electronicarts/CnC_Remastered_Collection 15 16 /* $Header: /CounterStrike/IPXMGR.H 1 3/03/97 10:24a Joe_bostic $ */ 17 /*************************************************************************** 18 ** C O N F I D E N T I A L --- W E S T W O O D S T U D I O S ** 19 *************************************************************************** 20 * * 21 * Project Name : Command & Conquer * 22 * * 23 * File Name : IPXMGR.H * 24 * * 25 * Programmer : Bill Randolph * 26 * * 27 * Start Date : December 19, 1994 * 28 * * 29 * Last Update : April 3, 1995 [BR] * 30 * * 31 *-------------------------------------------------------------------------* 32 * * 33 * This is the Connection Manager for IPX network communications. It * 34 * creates, manages, & orchestrates multiple IPX connections, as well as * 35 * the "global" connection ("Global Channel"), which can talk to any * 36 * system on the net. * 37 * * 38 * Use the Global Channel to query systems for their names, ID's, & * 39 * IPX addresses. Then, create a Private Connection with each system * 40 * that joins your game, and use the Private Channel to send game packets * 41 * (the private channel will perform somewhat faster, & gives you better * 42 * control than the Global Channel; it can detect retries, and the Global * 43 * Channel can't). * 44 * * 45 * HOW THIS CLASS WORKS: * 46 * This class has to set up an IPX Event Service Routine in low (DOS) * 47 * memory. So, it uses DPMI to allocate & lock a chunk of DOS memory; * 48 * this memory is used for all incoming packet buffers, the outgoing * 49 * packet buffer, and the actual code for the event handler. The real- * 50 * mode handler code & this class share a portion of memory that's mapped * 51 * into a "RealModeDataType" structure. As packets come in, the handler * 52 * points IPX to the next available packet buffer & restarts listening; * 53 * it sets a flag to tell this class that a packet is present at that * 54 * buffer slot. This class must read all the packets & determine which * 55 * connection they go with (the Global Channel, or one of the Private * 56 * Channels). This parsing is done in the Service routine for this class. * 57 * * 58 * Constructor: Just inits some variables, checks to see if IPX is there * 59 * Destructor: Complete shutdown; stops IPX listening, frees all memory * 60 * Init: Should only be called once (but can be called more); * 61 * allocates all memory, creates the Global Channel * 62 * connection, starts IPX listening. By not placing this * 63 * step in the constructor, the app can control when * 64 * listening actually starts; also, you don't get a bunch * 65 * of allocations just by declaring an IPXManagerClass * 66 * instance. You have to call Init() for the allocations * 67 * to occur. * 68 * Connection utilities: Create & manage Private Connections. Each * 69 * connection has its own IPX address, numerical ID, and * 70 * character name (presumably the name of the other * 71 * player). * 72 * Send/Get_Global_Message: adds a packet to the Global Connection queue, * 73 * or reads from the queue. The caller should check the * 74 * ProductID value from returned packets to be sure it's * 75 * talking to the right product. * 76 * Send/Get_Private_Message: adds a packet to a Private Connection queue, * 77 * or reads from the queue * 78 * Service: Checks the Real-Mode-Memory packet array to see if any * 79 * new packets have come in; if they have, it parses them * 80 * & distributes them to the right connection queue. The * 81 * queue's Service routine handles ACK'ing or Resending * 82 * packets. * 83 * * 84 * Here's a memory map of the Real-Mode memory block. 'N' is the number * 85 * of packet buffers allocated in low memory: * 86 * * 87 * ---------------------------------- * 88 * | Shared-memory data | * 89 * |--------------------------------| * 90 * | Real-mode event handler code | * 91 * |--------------------------------| * 92 * | IPX Header & Packet Buffer 0 | * 93 * |--------------------------------| * 94 * | IPX Header & Packet Buffer 1 | * 95 * |--------------------------------| * 96 * | IPX Header & Packet Buffer 2 | * 97 * |--------------------------------| * 98 * | . . . | * 99 * |--------------------------------| * 100 * | IPX Header & Packet Buffer N | * 101 * |--------------------------------| * 102 * | Send Event Control Block | * 103 * |--------------------------------| * 104 * | Send IPX Header | * 105 * |--------------------------------| * 106 * | Send Packet Buffer | * 107 * |--------------------------------| * 108 * | Flags Array [N] | * 109 * ---------------------------------- * 110 * * 111 * - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */ 112 113 #ifndef IPXMANAGER_H 114 #define IPXMANAGER_H 115 116 117 /* 118 ********************************* Includes ********************************** 119 */ 120 #include "ipxconn.h" 121 #include "ipxgconn.h" 122 #include "ipxaddr.h" 123 #include "connmgr.h" 124 125 /* 126 ********************************** Defines ********************************** 127 */ 128 /*--------------------------------------------------------------------------- 129 This is Virgin Interactive Entertainment's registered socket ID. 130 ---------------------------------------------------------------------------*/ 131 #define VIRGIN_SOCKET 0x8813 132 133 /*--------------------------------------------------------------------------- 134 This is the maximum number of IPX connections supported. Just change this 135 value to support more. 136 ---------------------------------------------------------------------------*/ 137 #define CONNECT_MAX 7 138 139 /*--------------------------------------------------------------------------- 140 These routines report the location & length of the real-mode routine, as 141 it's stored in protected-mode memory. 142 ---------------------------------------------------------------------------*/ 143 extern "C" { 144 void * __cdecl Get_RM_IPX_Address(void); 145 long __cdecl Get_RM_IPX_Size(void); 146 } 147 148 /* 149 ***************************** Class Declaration ***************************** 150 */ 151 class IPXManagerClass : public ConnManClass 152 { 153 /* 154 ---------------------------- Public Interface ---------------------------- 155 */ 156 public: 157 /*..................................................................... 158 Constructor/destructor. 159 .....................................................................*/ 160 IPXManagerClass (int glb_maxlen, int pvt_maxlen, int glb_num_packets, 161 int pvt_num_packets, unsigned short socket, unsigned short product_id); 162 virtual ~IPXManagerClass (); // stop listening 163 164 /*..................................................................... 165 Initialization routines. 166 .....................................................................*/ 167 int Init (void); 168 int Is_IPX(void); 169 virtual void Set_Timing (unsigned long retrydelta, unsigned long maxretries, 170 unsigned long timeout); 171 void Set_Bridge(NetNumType bridge); 172 173 /*..................................................................... 174 These routines control creation of the "Connections" (data queues) for 175 each remote system. 176 .....................................................................*/ 177 int Create_Connection(int id, char *name, IPXAddressClass *address); 178 int Delete_Connection(int id); 179 virtual int Num_Connections(void); 180 virtual int Connection_ID(int index); 181 char *Connection_Name(int id); 182 IPXAddressClass * Connection_Address(int id); 183 virtual int Connection_Index(int id); 184 void Set_Connection_Parms(int index, int id, char *name); 185 186 /*..................................................................... 187 This is how the application sends & receives messages. 188 .....................................................................*/ 189 int Send_Global_Message (void *buf, int buflen, int ack_req = 0, 190 IPXAddressClass *address = NULL); 191 int Get_Global_Message (void *buf, int *buflen, IPXAddressClass *address, 192 unsigned short *product_id); 193 194 virtual int Send_Private_Message (void *buf, int buflen, 195 int ack_req = 1, int conn_id = CONNECTION_NONE); 196 virtual int Get_Private_Message (void *buf, int *buflen, int *conn_id); 197 198 /*..................................................................... 199 The main polling routine; should be called as often as possible. 200 .....................................................................*/ 201 virtual int Service (void); 202 203 /*..................................................................... 204 This routine reports which connection has an error on it. 205 .....................................................................*/ 206 int Get_Bad_Connection(void); 207 208 /*..................................................................... 209 Queue utility routines. The application can determine how many 210 messages are in the send/receive queues. 211 .....................................................................*/ 212 virtual int Global_Num_Send(void); 213 virtual int Global_Num_Receive(void); 214 virtual int Private_Num_Send(int id = CONNECTION_NONE); 215 virtual int Private_Num_Receive(int id = CONNECTION_NONE); 216 217 /*..................................................................... 218 This routine changes the socket ID assigned the IPX Manager when it 219 was constructed. Do not call this function after calling Init()! 220 The Socket ID should be known by both ends of the communications before 221 any packets are sent. 222 .....................................................................*/ 223 void Set_Socket(unsigned short socket); 224 225 /*..................................................................... 226 Routines to return the largest average queue response time, and to 227 reset the response time for all queues. 228 .....................................................................*/ 229 virtual unsigned long Response_Time(void); 230 unsigned long Global_Response_Time(void); 231 virtual void Reset_Response_Time(void); 232 233 /*..................................................................... 234 This routine returns a pointer to the oldest non-ACK'd buffer I've sent. 235 .....................................................................*/ 236 void * Oldest_Send(void); 237 238 /*..................................................................... 239 Debug routines 240 .....................................................................*/ 241 virtual void Configure_Debug(int index, int type_offset, int type_size, 242 char **names, int namestart, int namecount); 243 virtual void Mono_Debug_Print(int index, int refresh = 0); 244 245 /* 246 --------------------------- Private Interface ---------------------------- 247 */ 248 private: 249 /*..................................................................... 250 These routines allocate & free the DOS Real-mode memory block. 251 .....................................................................*/ 252 int Alloc_RealMode_Mem(void); 253 int Free_RealMode_Mem(void); 254 255 /*..................................................................... 256 Misc variables 257 .....................................................................*/ 258 unsigned int IPXStatus : 1; // 0 = no IPX, 1 = IPX found 259 unsigned int Listening : 1; // 1 = Listening is on 260 unsigned int RealMemAllocd : 1; // 1 = Real-mode memory has been alloc'd 261 262 /*..................................................................... 263 Packet Sizes, used for allocating real-mode memory 264 .....................................................................*/ 265 int Glb_MaxPacketLen; // Global Channel maximum packet size 266 int Glb_NumPackets; // # Global send/receive packets 267 int Pvt_MaxPacketLen; // Private Channel maximum packet size 268 int Pvt_NumPackets; // # Private send/receive packets 269 270 /*..................................................................... 271 The ProductID is used in the Global Channel's packet header, and it's 272 used for the Private Channels' Magic Number. 273 .....................................................................*/ 274 unsigned short ProductID; // product ID 275 276 /*..................................................................... 277 The Socket ID, and local Novell Connection Number 278 .....................................................................*/ 279 unsigned short Socket; // Our socket ID for sending/receiving 280 int ConnectionNum; // local connection #, 0=not logged in 281 282 /*..................................................................... 283 Array of connection queues 284 .....................................................................*/ 285 IPXConnClass * Connection[CONNECT_MAX]; // array of connection object ptrs 286 int NumConnections; // # connection objects in use 287 IPXGlobalConnClass *GlobalChannel; // the Global Channel 288 289 /*..................................................................... 290 Current queue for polling for received packets 291 .....................................................................*/ 292 int CurConnection; 293 294 /*..................................................................... 295 Timing parameters for all connections 296 .....................................................................*/ 297 unsigned long RetryDelta; 298 unsigned long MaxRetries; 299 unsigned long Timeout; 300 301 /*--------------------------------------------------------------------- 302 Real-mode memory pointers and such 303 ---------------------------------------------------------------------*/ 304 /*..................................................................... 305 This is a structure that mirrors data in real-mode memory: 306 .....................................................................*/ 307 typedef struct { 308 short Marker1; // the byte ID marker 309 ECBType ListenECB; // the Listening ECB 310 short NumBufs; // # of buffers we're giving to the handler 311 char *BufferFlags; // array of buffer-avail flags 312 short PacketSize; // size of packet including IPX header 313 IPXHeaderType *FirstPacketBuf; // ptr to 1st packet buffer 314 short CurIndex; // handler's current packet index 315 IPXHeaderType *CurPacketBuf; // handler's current packet buf 316 short FuncOffset; // contains offset of code 317 char Semaphore; // prevents re-entrancy 318 short ReEntrantCount; // times we've been called re-entrantly 319 short StackPtr; // real-mode stack pointer 320 short StackSeg; // real-mode stack segment 321 short StackPtr_int; // internal stack pointer 322 short StackSeg_int; // internal stack segment 323 short StackCheck; // stack check value (0x1234) 324 short Stack[256]; // actual stack space 325 short StackSpace; // label for top of stack 326 short Marker2; // the byte ID marker 327 } RealModeDataType; 328 329 /*..................................................................... 330 The number & size of packet buffers in low memory 331 .....................................................................*/ 332 int NumBufs; // # packet buffers allocated 333 int PacketLen; // size of packet without IPX header 334 int FullPacketLen; // size of packet including IPX header 335 336 /*..................................................................... 337 Selector & Segment of the DOS allocation; 338 Size of the allocation; 339 Ptr to the real-mode assembly data area 340 .....................................................................*/ 341 unsigned short Selector; // selector of DOS allocation pointer 342 unsigned short Segment; // real-mode segment of DOS allocation 343 int RealMemSize; // size of real mode memory allocated 344 RealModeDataType *RealModeData; // assembly routine & its data 345 346 /*..................................................................... 347 This is a real-mode pointer to the address of the real-mode assembly 348 entry point. 349 .....................................................................*/ 350 long Handler; 351 352 /*..................................................................... 353 Event Control Block for listening; contained within the real-mode 354 assembly routine's data area 355 .....................................................................*/ 356 ECBType *ListenECB; // ECB for listening 357 358 /*..................................................................... 359 ptr to the 1st header & data buffers in the packet buffer array 360 .....................................................................*/ 361 IPXHeaderType *FirstHeaderBuf; // array of packet headers & buffers 362 char *FirstDataBuf; // 1st data buffer area 363 364 /*..................................................................... 365 Current packet index & ptrs for parsing packets 366 .....................................................................*/ 367 int CurIndex; // Current packet index, for reading 368 IPXHeaderType *CurHeaderBuf; // Current packet ptr, for reading 369 char *CurDataBuf; // Current actual data ptr 370 371 /*..................................................................... 372 ECB, header, & buffer for sending 373 .....................................................................*/ 374 ECBType *SendECB; // ECB for sending 375 IPXHeaderType *SendHeader; // Header for sending 376 char *SendBuf; // buffer for sending 377 378 /*..................................................................... 379 Flags indicating whether a buffer contains data or not (1 = full) 380 The IPXManager must clear this flag; the real-mode routine will set it. 381 .....................................................................*/ 382 char *BufferFlags; // array of rx-buffer-avail flags 383 384 /*..................................................................... 385 Various Statistics 386 .....................................................................*/ 387 int SendOverflows; 388 int ReceiveOverflows; 389 int BadConnection; 390 }; 391 392 #endif 393 394 /*************************** end of ipxmgr.h *******************************/