CnC_Remastered_Collection

Command and Conquer: Red Alert
Log | Files | Refs | README | LICENSE

INTERNET.CPP (30411B)


      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 /*************************************************************************************
     17  **   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                  **
     18  *************************************************************************************
     19  *                                                                                   *
     20  *                 Project Name : Command & Conquer - Red Alert                      *
     21  *                                                                                   *
     22  *                    File Name : INTERNET.CPP                                       *
     23  *                                                                                   *
     24  *                   Programmer : Steve Tall                                         *
     25  *                                                                                   *
     26  *                   Start Date : March 11th, 1996                                   *
     27  *                                                                                   *
     28  *                  Last Update : August 5th, 1996 [ST]                              *
     29  *                                                                                   *
     30  *-----------------------------------------------------------------------------------*
     31  * Overview:                                                                         *
     32  *                                                                                   *
     33  *  Miscellaneous junk related to H2H internet connection.                           *
     34  *                                                                                   *
     35  *-----------------------------------------------------------------------------------*
     36  * Functions:                                                             	 			*
     37  *  Check_From_WChat -- Interprets start game packet from WChat           	 			*
     38  *  Read_Game_Options -- Read the game setup options from the wchat packet	 			*
     39  *  Is_User_WChat_Registered -- retrieve the users wchat entry from registry 			*
     40  *  Spawn_WChat -- spawns or switches focus to wchat                         			*
     41  *  Spawn_Registration_App -- spawns the C&C/Planet westwood registration app			*
     42  *  Do_The_Internet_Menu_Thang -- Handle case where user clicks on 'Internet' button *
     43  *                                                                         				*
     44  *                                                                         				*
     45  *                                                                         				*
     46  * - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
     47 
     48 
     49 #include "function.h"
     50 #include "tcpip.h"
     51 #include "ccdde.h"
     52 
     53 
     54 
     55 /***************************************************************************
     56 ** Internet specific globals
     57 */
     58 char PlanetWestwoodHandle[] = {"Handle"};				//Planet WW user name
     59 char PlanetWestwoodPassword[] = {"Password"};       //Planet WW password
     60 char PlanetWestwoodIPAddress[IP_ADDRESS_MAX] = {"206.154.108.87"};	//IP of server or other player
     61 long PlanetWestwoodPortNumber = 1234;					//Port number to send to
     62 bool PlanetWestwoodIsHost = false;                  //Flag true if player has control of game options
     63 unsigned long PlanetWestwoodGameID;                 //Game ID
     64 unsigned long PlanetWestwoodStartTime;              //Time that game was started
     65 HWND	WChatHWND = 0;                               //Handle to Wchat window.
     66 bool UseVirtualSubnetServer;
     67 int  InternetMaxPlayers;
     68 int WChatMaxAhead;
     69 int WChatSendRate;
     70 
     71 
     72 int Read_Game_Options(void);
     73 
     74 extern bool SpawnedFromWChat;
     75 
     76 
     77 
     78 
     79 
     80 
     81 /***********************************************************************************************
     82  * Check_From_WChat -- This function reads in C&CSPAWN.INI and interprets it                   *
     83  *                     C&CSPAWN.INI is now sent to us by WCHAT via DDE                         *
     84  *                                                                                             *
     85  *                                                                                             *
     86  *                                                                                             *
     87  * INPUT:    Name of C&CSPAWN.INI file. If NULL then get file from DDE Server                  *
     88  *                                                                                             *
     89  * OUTPUT:   Nothing                                                                           *
     90  *                                                                                             *
     91  * WARNINGS: None                                                                              *
     92  *                                                                                             *
     93  * HISTORY:                                                                                    *
     94  *    6/9/96 1:44PM ST : Created                                                               *
     95  *=============================================================================================*/
     96 void Check_From_WChat(char *wchat_name)
     97 {
     98 #ifndef DEMO
     99 
    100 	char	default_string[] = {"Error"};
    101 	char	key_string[256];
    102 	char *ini_file;
    103 	RawFileClass wchat_file;
    104 
    105 	/*
    106 	** Get a pointer to C&CSPAWN.INI either by reading it from disk or getting it from
    107 	** the DDE server.
    108 	*/
    109 	if (wchat_name){
    110 		ini_file = new char [8192];
    111 	}else{
    112 		ini_file = DDEServer.Get_MPlayer_Game_Info();
    113 #if (0)
    114 		/*
    115 		** Save it to disk as well so I can see it
    116 		*/
    117 		RawFileClass anotherfile ("FROMCHAT.TXT");
    118 		anotherfile.Write(ini_file, DDEServer.Get_MPlayer_Game_Info_Length());
    119 #endif	//(0)
    120 	}
    121 
    122 	if (wchat_name){
    123 		wchat_file.Set_Name(wchat_name);
    124 	}
    125 
    126 	if (!wchat_name || wchat_file.Is_Available()){
    127 
    128 		/*
    129 		** Read the ini file from disk if we founf it there
    130 		*/
    131 		if (wchat_name){
    132 			wchat_file.Read(ini_file, wchat_file.Size());
    133 		}
    134 
    135 		/*
    136 		** Get the IP address
    137 		*/
    138 		key_string[0] = 0;
    139 
    140 		WWGetPrivateProfileString("Internet",
    141 										"Address",
    142 										default_string,
    143 										key_string,
    144 										sizeof(key_string),
    145 										ini_file);
    146 
    147 
    148 		if (!strcmp (key_string, default_string)) {
    149 			if (wchat_name) delete ini_file;
    150 			return;
    151 		}
    152 		strcpy (PlanetWestwoodIPAddress, key_string);
    153 
    154 
    155 
    156 		/*
    157 		** Get the port number
    158 		*/
    159 		key_string[0] = 0;
    160 
    161 		WWGetPrivateProfileString("Internet",
    162 										"Port",
    163 										default_string,
    164 										key_string,
    165 										sizeof(key_string),
    166 										ini_file);
    167 
    168 
    169 		if (!strcmp (key_string, default_string)) {
    170 			if (wchat_name) delete ini_file;
    171 			return;
    172 		}
    173 
    174 		PlanetWestwoodPortNumber = atol(key_string);
    175 
    176 
    177 		/*
    178 		** Get host or client
    179 		*/
    180 		key_string[0] = 0;
    181 
    182 		WWGetPrivateProfileString("Internet",
    183 										"Host",
    184 										default_string,
    185 										key_string,
    186 										sizeof(key_string),
    187 										ini_file);
    188 
    189 
    190 		if (!strcmp (key_string, default_string)) {
    191 			if (wchat_name) delete ini_file;
    192 			return;
    193 		}
    194 
    195 		if (strchr (key_string, '1')){
    196 			PlanetWestwoodIsHost = true;
    197 		}else{
    198 			PlanetWestwoodIsHost = false;
    199 		}
    200 
    201 		UseVirtualSubnetServer = WWGetPrivateProfileInt("Internet", "UseVSS", 0, ini_file);
    202 
    203 		Special.IsFromWChat = true;
    204 	}
    205 
    206 	if (wchat_name) delete ini_file;
    207 
    208 #else	//DEMO
    209 
    210 	wchat_name = wchat_name;
    211 
    212 #endif	//DEMO
    213 
    214 }
    215 
    216 //EventClass Wibble;
    217 
    218 
    219 /***************************************************************************
    220  * Read_Game_Options -- reads multiplayer game options from disk           *
    221  *                                                                         *
    222  * This routine is used for multiplayer games which read the game options	*
    223  * from disk, rather than through a connection dialog.							*
    224  *                                                                         *
    225  * INPUT:                                                                  *
    226  *		name of C&CSPAWN.INI file. Null if data should be got from DDE server*                                                                         *
    227  * OUTPUT:                                                                 *
    228  *		1 = OK, 0 = error																		*
    229  *                                                                         *
    230  * WARNINGS:                          \                                     *
    231  *		none.																						*
    232  *                                                                         *
    233  * HISTORY:                                                                *
    234  *   01/11/1996 BRR : Created.                                             *
    235  *=========================================================================*/
    236 int Read_Game_Options(char *name)
    237 {
    238 	char *buffer;
    239 
    240 	char filename[256] = {"INVALID.123"};
    241 
    242 	if (name){
    243 		strcpy (filename, name);
    244 	}
    245 
    246 	/*------------------------------------------------------------------------
    247 	Create filename and read the file.
    248 	------------------------------------------------------------------------*/
    249 	CCFileClass file (filename);
    250 
    251 	if (name && !file.Is_Available()) {
    252 		return(0);
    253 	} else {
    254 		if (name){
    255 			buffer = new char [8192];							// INI staging buffer pointer.
    256 			memset(buffer, '\0', 8192);
    257 			file.Read(buffer, 8192-1);
    258 			file.Close();
    259 		}else{
    260 			buffer = DDEServer.Get_MPlayer_Game_Info();
    261 		}
    262 	}
    263 
    264 	/*------------------------------------------------------------------------
    265 	Get the player's name
    266 	------------------------------------------------------------------------*/
    267 	WWGetPrivateProfileString("Options", "Handle", "Noname", MPlayerName,
    268 		sizeof(MPlayerName), buffer);
    269 	strcpy(MPlayerGameName, MPlayerName);
    270 	MPlayerColorIdx = WWGetPrivateProfileInt("Options", "Color", 0, buffer);
    271 	MPlayerPrefColor = MPlayerColorIdx;
    272 	MPlayerHouse = (HousesType)WWGetPrivateProfileInt("Options", "Side",
    273 		HOUSE_GOOD, buffer);
    274 
    275 	MPlayerCredits = WWGetPrivateProfileInt("Options", "Credits", 0, buffer);
    276 	MPlayerBases = WWGetPrivateProfileInt("Options", "Bases", 0, buffer);
    277 	MPlayerTiberium = WWGetPrivateProfileInt("Options", "Tiberium", 0, buffer);
    278 	MPlayerGoodies = WWGetPrivateProfileInt("Options", "Crates", 0, buffer);
    279 	MPlayerGhosts = WWGetPrivateProfileInt("Options", "AI", 0, buffer);
    280 	BuildLevel = WWGetPrivateProfileInt("Options", "BuildLevel", 0, buffer);
    281 	MPlayerUnitCount = WWGetPrivateProfileInt("Options", "UnitCount", 0, buffer);
    282 	Seed = WWGetPrivateProfileInt("Options", "Seed", 0, buffer);
    283 	Special.IsCaptureTheFlag = WWGetPrivateProfileInt("Options", "CaptureTheFlag", 0, buffer);
    284 	PlanetWestwoodGameID = WWGetPrivateProfileInt("Internet", "GameID", 0, buffer);
    285 	PlanetWestwoodStartTime = WWGetPrivateProfileInt ("Internet", "StartTime", 0, buffer);
    286 	WChatHWND = (HWND) WWGetPrivateProfileInt("Internet", "HWND", (int)FindWindow("OWL_Window", "Westwood Chat"), buffer);
    287 
    288 	InternetMaxPlayers = WWGetPrivateProfileInt("Internet", "MaxPlayers", 2, buffer);
    289 
    290 
    291 	if (MPlayerTiberium) {
    292 		Special.IsTGrowth = 1;
    293 		Special.IsTSpread = 1;
    294 	} else {
    295 		Special.IsTGrowth = 0;
    296 		Special.IsTSpread = 0;
    297 	}
    298 	ScenarioIdx = WWGetPrivateProfileInt("Options", "Scenario", 0, buffer);
    299 	Scenario = ScenarioIdx;	//MPlayerFilenum[ScenarioIdx];
    300 
    301 	Options.GameSpeed = 0;
    302 
    303 	MPlayerLocalID = Build_MPlayerID (MPlayerColorIdx, MPlayerHouse);
    304 
    305 	MPlayerMaxAhead = WChatMaxAhead = WWGetPrivateProfileInt("Timing", "MaxAhead", 9, buffer);
    306 	FrameSendRate = WChatSendRate = WWGetPrivateProfileInt("Timing", "SendRate", 3, buffer);
    307 
    308 	if (name) delete buffer;
    309 	return (1);
    310 
    311 }
    312 
    313 
    314 
    315 
    316 /***********************************************************************************************
    317  * Get_Registry_Sub_Key -- search a registry key for a sub-key                                 *
    318  *                                                                                             *
    319  *                                                                                             *
    320  *                                                                                             *
    321  * INPUT:    handle of key to search                                                           *
    322  *           text to search for                                                                *
    323  *           true if old key should be closed when new key opened                              *
    324  *                                                                                             *
    325  * OUTPUT:   handle to the key we found or 0                                                   *
    326  *                                                                                             *
    327  * WARNINGS: None                                                                              *
    328  *                                                                                             *
    329  * HISTORY:                                                                                    *
    330  *    1/12/96 2:11PM ST : Created                                                              *
    331  *=============================================================================================*/
    332 
    333 extern HKEY Get_Registry_Sub_Key (HKEY base_key, char *search_key, BOOL close);
    334 
    335 
    336 
    337 void Just_Path(char *path, char *destpath)
    338 {
    339 	char *terminator = NULL;		//He'll be back.
    340 
    341 	strcpy  (destpath, path);
    342 	terminator = strrchr (destpath, '\\');
    343 	if (terminator){
    344 		*terminator = 0;
    345 	}
    346 }
    347 
    348 
    349 
    350 
    351 
    352 /***********************************************************************************************
    353  * Is_User_WChat_Registered -- retrieve the users wchat entry from the registry                *
    354  *                                                                                             *
    355  *                                                                                             *
    356  *                                                                                             *
    357  * INPUT:  Nothing                                                                             *
    358  *                                                                                             *
    359  * OUTPUT:   TRUE if users wchat entry was found in the registry                               *
    360  *                                                                                             *
    361  * WARNINGS: None                                                                              *
    362  *                                                                                             *
    363  * HISTORY:                                                                                    *
    364  *    1/12/96 2:13PM ST : Created                                                              *
    365  *=============================================================================================*/
    366 bool Is_User_WChat_Registered(char *buffer, int buffer_len)
    367 {
    368 	buffer;
    369 	buffer_len;
    370 	return false;
    371 
    372 #if (0)	//ST - 1/2/2019 5:54PM
    373 	
    374 	HKEY	key;
    375 	char	user_handle[256];
    376 	DWORD	user_handle_size = sizeof (user_handle);
    377 	char	user_pword[256];
    378 	DWORD	user_pword_size = sizeof (user_pword);
    379 
    380 
    381 	/*
    382 	** Check HKEY_CLASSES_ROOT first. Old versions of Wchat register there
    383 	*/
    384 	key = Get_Registry_Sub_Key (HKEY_CLASSES_ROOT, "Wchat", FALSE);
    385 
    386 	if (key){
    387 		key = Get_Registry_Sub_Key (key, "Nick1", TRUE);
    388 		if (key){
    389 
    390 			if (RegQueryValue(key, "Nick", user_handle, (long*)&user_handle_size) == ERROR_SUCCESS){
    391 
    392 				if (RegQueryValue(key, "Pass", user_pword, (long*)&user_pword_size) == ERROR_SUCCESS){
    393 
    394 					/*
    395 					** If the first char of the users name is non-numberic and there is a password
    396 					** then return success
    397 					*/
    398 					if ((user_handle[0] < '0' || user_handle[0] > '9') && user_pword[0]){
    399 						RegCloseKey( key );
    400 						return (TRUE);
    401 					}
    402 				}
    403 			}
    404 		}
    405 
    406 		RegCloseKey ( key );
    407 	}
    408 
    409 
    410 
    411 	/*
    412 	** Check HKEY_LOCAL_MACKINE/Software
    413 	*/
    414 	user_handle_size = sizeof (user_handle);
    415 
    416 	key = Get_Registry_Sub_Key (HKEY_LOCAL_MACHINE, "SOFTWARE", FALSE);
    417 	if (!key) return (FALSE);
    418 
    419 	key = Get_Registry_Sub_Key (key, "Westwood", TRUE);
    420 	if (!key) return (FALSE);
    421 
    422 	key = Get_Registry_Sub_Key (key, "InetReg", TRUE);
    423 	if (!key) return (FALSE);
    424 
    425 	//key = Get_Registry_Sub_Key (key, "UserName", TRUE);
    426 	//if (!key) return (FALSE);
    427 
    428 	//key = Get_Registry_Sub_Key (key, "Nick", TRUE);
    429 	//if (!key) return (FALSE);
    430 
    431 	if (RegQueryValueEx(key, "UserName", NULL, NULL, (unsigned char*)user_handle, &user_handle_size) != ERROR_SUCCESS){
    432 		RegCloseKey(key);
    433 		return (FALSE);
    434 	}
    435 
    436 	RegCloseKey(key);
    437 	memcpy (buffer, user_handle, min((unsigned)buffer_len, user_handle_size));
    438 
    439 	/*
    440 	** If the first char of the users name is non-numeric then return success
    441 	*/
    442 	if (user_handle[0] < '0' || user_handle[0] > '9'){
    443 		return (TRUE);
    444 	}else{
    445 		return (FALSE);
    446 	}
    447 #endif
    448 }
    449 
    450 
    451 
    452 /***********************************************************************************************
    453  * Spawn_WChat -- spawns or switches focus to wchat                                            *
    454  *                                                                                             *
    455  *                                                                                             *
    456  *                                                                                             *
    457  * INPUT:    can launch. If set then we are allowed to launch WChat if not already running     *
    458  *                                                                                             *
    459  * OUTPUT:   True if wchat was spawned                                                         *
    460  *                                                                                             *
    461  * WARNINGS: None                                                                              *
    462  *                                                                                             *
    463  * HISTORY:                                                                                    *
    464  *    6/8/96 12:33PM ST : Created                                                              *
    465  *=============================================================================================*/
    466 bool Poke_WChat(void);
    467 bool Spawn_WChat(bool can_launch)
    468 {
    469 	can_launch;
    470 	return false;
    471 
    472 #if (0)
    473 	CCDebugString ("C&C95 - In Spawn_WChat.\n");
    474 	char packet[10] = {"Hello"};
    475 	HWND chat_window = NULL;
    476 
    477 	/*
    478 	** See if WChat is already running...
    479 	*/
    480 	if (WChatHWND && IsWindow (WChatHWND) ){
    481 		chat_window = WChatHWND;
    482 	}else{
    483 		chat_window = FindWindow ( "OWL_Window", "Westwood Chat" );
    484 	}
    485 
    486 	if (chat_window){
    487 	/*
    488 	** WChat is already running. Minimize myself then try to give it focus.
    489 	*/
    490 		Set_Palette(BlackPalette);
    491 		VisiblePage.Clear();
    492 		ShowWindow (MainWindow, SW_MINIMIZE);
    493 		/*
    494 		** Give windoze a couple of secs to sort itself out.
    495 		*/
    496 		CountDownTimerClass wibble_timer;
    497 		wibble_timer.Set ( 60 * 3, true);
    498 
    499 		while (wibble_timer.Time()){
    500 			/*
    501 			** Call our message loop to make sure we get all the messages that are sent to us
    502 			** when we minimise.
    503 			*/
    504 			Keyboard::Check();
    505 		}
    506 
    507 		/*
    508 		** Send chat a tickle message so it knows to send the game stats to the server.
    509 		*/
    510 		if (GameStatisticsPacketSent && !PlanetWestwoodIsHost) {
    511 			Send_Data_To_DDE_Server (packet, strlen(packet), DDEServerClass::DDE_TICKLE);
    512 		}
    513 		/*
    514 		** Give the focus to WChat
    515 		*/
    516 		SetForegroundWindow ( chat_window );
    517 		ShowWindow ( chat_window, SW_RESTORE );
    518 		return(true);
    519 	}
    520 
    521 	/*
    522 	** Fail if we aren't allowed to launch wchat and we couldnt find its window.
    523 	*/
    524 	if (!can_launch) return (false);
    525 
    526 	/*
    527 	** Find where WChat was installed to
    528 	*/
    529 
    530 	HKEY	key;
    531 	char	wchat_loc[256];
    532 	DWORD	wchat_loc_size = 256;
    533 
    534 	key = Get_Registry_Sub_Key (HKEY_LOCAL_MACHINE, "SOFTWARE", FALSE);
    535 	if (!key) return (FALSE);
    536 
    537 	key = Get_Registry_Sub_Key (key, "Westwood", TRUE);
    538 	if (!key) return (FALSE);
    539 
    540 	key = Get_Registry_Sub_Key (key, "WChat", TRUE);
    541 	if (!key) return (FALSE);
    542 
    543 	//key = Get_Registry_Sub_Key (key, "UserName", TRUE);
    544 	//if (!key) return (FALSE);
    545 
    546 	//key = Get_Registry_Sub_Key (key, "Nick", TRUE);
    547 	//if (!key) return (FALSE);
    548 
    549 	if (RegQueryValueEx(key, "InstallPath", NULL, NULL, (unsigned char*)wchat_loc, &wchat_loc_size) != ERROR_SUCCESS){
    550 		RegCloseKey(key);
    551 		return (FALSE);
    552 	}
    553 
    554 	RegCloseKey(key);
    555 
    556 	PROCESS_INFORMATION process_info;
    557 	STARTUPINFO start_info;
    558 	memset ((void*)&start_info, 0, sizeof(start_info));
    559 	start_info.cb = sizeof(start_info);
    560 	char justpath [256];
    561 	Just_Path(wchat_loc, justpath);
    562 
    563 	/*
    564 	** We found WChat in the registry. Minimize myself then try to spawn it.
    565 	*/
    566 	Set_Palette(BlackPalette);
    567 	VisiblePage.Clear();
    568 	ShowWindow (MainWindow, SW_MINIMIZE);
    569 	/*
    570 	** Give windoze a couple of secs to sort itself out.
    571 	*/
    572 	CountDownTimerClass wibble_timer;
    573 	wibble_timer.Set ( 60 * 3, true);
    574 
    575 	while (wibble_timer.Time()){
    576 		/*
    577 		** Call our message loop to make sure we get all the messages that are sent to us
    578 		** when we minimise.
    579 		*/
    580 		Keyboard::Check();
    581 	}
    582 	bool success = CreateProcess (wchat_loc, NULL, NULL, NULL, false, 0, NULL, justpath, &start_info, &process_info);
    583 
    584 	if (success){
    585 		return (true);
    586 	}else{
    587 		ShowWindow (MainWindow, SW_RESTORE);
    588 		while ( Keyboard::Check() ) {};
    589 		return (false);
    590 	}
    591 #endif
    592 
    593 }
    594 
    595 
    596 
    597 
    598 /***********************************************************************************************
    599  * Spawn_Registration_App -- spawns the C&C/Planet westwood registration app                   *
    600  *                                                                                             *
    601  *                                                                                             *
    602  *                                                                                             *
    603  * INPUT:    Nothing                                                                           *
    604  *                                                                                             *
    605  * OUTPUT:   True if app was spawned                                                           *
    606  *                                                                                             *
    607  * WARNINGS: None                                                                              *
    608  *                                                                                             *
    609  * HISTORY:                                                                                    *
    610  *    6/8/96 12:33PM ST : Created                                                              *
    611  *=============================================================================================*/
    612 bool Spawn_Registration_App(void)
    613 {
    614 	return false;
    615 #if (0)	//ST - 1/2/2019 5:53PM
    616 	/*
    617 	** Find where inetreg was installed to
    618 	*/
    619 
    620 	HKEY	key;
    621 	char	inetreg_loc[256];
    622 	DWORD	inetreg_loc_size = 256;
    623 
    624 	key = Get_Registry_Sub_Key (HKEY_LOCAL_MACHINE, "SOFTWARE", FALSE);
    625 	if (!key) return (FALSE);
    626 
    627 	key = Get_Registry_Sub_Key (key, "Westwood", TRUE);
    628 	if (!key) return (FALSE);
    629 
    630 	key = Get_Registry_Sub_Key (key, "InetReg", TRUE);
    631 	if (!key) return (FALSE);
    632 
    633 	if (RegQueryValueEx(key, "InstallPath", NULL, NULL, (unsigned char*)inetreg_loc, &inetreg_loc_size) != ERROR_SUCCESS){
    634 		RegCloseKey(key);
    635 		return (FALSE);
    636 	}
    637 
    638 	RegCloseKey(key);
    639 
    640 	PROCESS_INFORMATION process_info;
    641 	STARTUPINFO start_info;
    642 	char justpath 	[256];
    643 	memset ((void*)&start_info, 0, sizeof(start_info));
    644 	start_info.cb = sizeof(start_info);
    645 	Just_Path(inetreg_loc, justpath);
    646 
    647 	BOOL success = CreateProcess (inetreg_loc, NULL, NULL, NULL, false, 0, NULL, justpath, &start_info, &process_info);
    648 	if (success){
    649 		//WaitForSingleObject (process_info.hProcess, 1000*10000);
    650 		//SetForegroundWindow ( MainWindow );
    651 		//ShowWindow ( MainWindow, SW_RESTORE );
    652 	}
    653 	return (success);
    654 #endif
    655 
    656 }
    657 
    658 
    659 
    660 
    661 
    662 /***********************************************************************************************
    663  * Do_The_Internet_Menu_Thang -- Handle case where user clicks on 'Internet' button            *
    664  *                                                                                             *
    665  *                                                                                             *
    666  *                                                                                             *
    667  * INPUT:    Nothing                                                                           *
    668  *                                                                                             *
    669  * OUTPUT:   Nothing                                                                           *
    670  *                                                                                             *
    671  * WARNINGS: None                                                                              *
    672  *                                                                                             *
    673  * HISTORY:                                                                                    *
    674  *    6/7/96 8:30PM ST : Created                                                               *
    675  *=============================================================================================*/
    676 bool Do_The_Internet_Menu_Thang(void)
    677 {
    678 #ifndef DEMO
    679 
    680 	int factor			= (SeenBuff.Get_Width() == 320) ? 1 : 2;
    681 
    682 	/*
    683 	** Dialog & button dimensions
    684 	*/
    685 	int d_dialog_w = 120 *factor;											// dialog width
    686 	int d_dialog_h = 80*factor;											// dialog height
    687 	int d_dialog_x = ((320*factor - d_dialog_w) / 2);				// dialog x-coord
    688 	int d_dialog_y = ((200*factor - d_dialog_h) / 2);				// centered y-coord
    689 	int d_dialog_cx = d_dialog_x + (d_dialog_w / 2);		// center x-coord
    690 
    691 	int d_margin1=10;
    692 	int d_txt6_h=15;
    693 
    694 #if (GERMAN | FRENCH)
    695 	int d_cancel_w = 50*factor;
    696 #else
    697 	int d_cancel_w = 40*factor;
    698 #endif
    699 	int d_cancel_h = 9*factor;
    700 	int d_cancel_x = d_dialog_cx - d_cancel_w / 2;
    701 	int d_cancel_y = d_dialog_y + d_dialog_h - 20*factor;
    702 
    703 	char packet[10] = {"Hello"};
    704 
    705 #if (GERMAN | FRENCH)
    706 	int	width=160*factor;
    707 	int	height=80*factor;
    708 #else
    709 	int	width=120*factor;
    710 	int	height=80*factor;
    711 #endif	//GERMAN | FRENCH
    712 
    713 	Fancy_Text_Print(TXT_NONE,0,0,TBLACK,TBLACK,TPF_6PT_GRAD | TPF_NOSHADOW);
    714 	Format_Window_String((char*)Text_String (TXT_CONNECTING), SeenBuff.Get_Height(), width, height);
    715 
    716 #if (GERMAN | FRENCH)
    717 	d_dialog_w = width + 25*factor;
    718 	d_dialog_x = ((320*factor - d_dialog_w) / 2);				// dialog x-coord
    719 	d_cancel_x = d_dialog_cx - (d_cancel_w / 2);
    720 #endif
    721 
    722 	/*
    723 	** Button Enumerations
    724 	*/
    725 	enum {
    726 		BUTTON_CANCEL = 100,
    727 	};
    728 
    729 	/*
    730 	** Buttons
    731 	*/
    732 	//TextButtonClass *buttons;										// button list
    733 
    734 	TextButtonClass cancelbtn(BUTTON_CANCEL, TXT_CANCEL,
    735 		TPF_CENTER | TPF_6PT_GRAD | TPF_USE_GRAD_PAL | TPF_NOSHADOW,
    736 //#if (GERMAN | FRENCH)
    737 //		d_cancel_x, d_cancel_y);
    738 //#else
    739 		d_cancel_x, d_cancel_y, d_cancel_w, d_cancel_h);
    740 //#endif
    741 
    742 	//buttons = &cancelbtn;
    743 
    744 	Fancy_Text_Print(TXT_NONE, 0, 0, CC_GREEN, TBLACK,
    745 		TPF_CENTER | TPF_6PT_GRAD | TPF_USE_GRAD_PAL | TPF_NOSHADOW);
    746 
    747 
    748 	char users_name[256];
    749 	int  buffer_len = sizeof (users_name);
    750 	bool process;
    751 	bool display;
    752 	KeyNumType input;
    753 
    754 
    755 	if (!Special.IsFromWChat && !SpawnedFromWChat){
    756 		/*
    757 		** If the user is registered with Planet Westwood then spawn WChat.
    758 		*/
    759 		if (Is_User_WChat_Registered(users_name, buffer_len)){
    760 			GameStatisticsPacketSent = false;
    761 			if (!Spawn_WChat(true)){
    762 				Set_Logic_Page(SeenBuff);
    763 				Load_Title_Screen("HTITLE.PCX", &HidPage, Palette);
    764 				Blit_Hid_Page_To_Seen_Buff();
    765 				Set_Palette(Palette);
    766 				CCMessageBox().Process(TXT_ERROR_UNABLE_TO_RUN_WCHAT, TXT_OK);
    767 				LogicPage->Clear();
    768 				return(false);
    769 			}
    770 		}else{
    771 			Set_Logic_Page(SeenBuff);
    772 			Load_Title_Screen("HTITLE.PCX", &HidPage, Palette);
    773 			Blit_Hid_Page_To_Seen_Buff();
    774 			Set_Palette(Palette);
    775 			if (CCMessageBox().Process(TXT_EXPLAIN_REGISTRATION, TXT_REGISTER, TXT_CANCEL)){
    776 				LogicPage->Clear();
    777 				return(false);
    778 			}else{
    779 				LogicPage->Clear();
    780 				Spawn_Registration_App();
    781 				return(false);
    782 			}
    783 		}
    784 	}
    785 
    786 	/*
    787 	**
    788 	** User is registered and we spawned WChat. Wait for a game start message from WChat.
    789 	**
    790 	*/
    791 
    792 	process = true;
    793 	display = true;
    794 
    795 	while (process){
    796 
    797 		/*
    798 		** If we have just received input focus again after running in the background then
    799 		** we need to redraw.
    800 		*/
    801 		if (AllSurfaces.SurfacesRestored){
    802 			AllSurfaces.SurfacesRestored = FALSE;
    803 			display = true;
    804 		}
    805 
    806 		if (display) {
    807 
    808 			Set_Logic_Page(SeenBuff);
    809 
    810 			Hide_Mouse();
    811 			/*
    812 			** Redraw backgound & dialog box
    813 			*/
    814 			Load_Title_Screen("HTITLE.PCX", &HidPage, Palette);
    815 			Blit_Hid_Page_To_Seen_Buff();
    816 			Set_Palette(Palette);
    817 
    818 			Dialog_Box(d_dialog_x, d_dialog_y, d_dialog_w, d_dialog_h);
    819 
    820 			/*
    821 			** Dialog & Field labels
    822 			*/
    823 			Draw_Caption (TXT_NONE, d_dialog_x, d_dialog_y, d_dialog_w);
    824 
    825 			Fancy_Text_Print(TXT_CONNECTING, d_dialog_cx-width/2, d_dialog_y + 25*factor, CC_GREEN, TBLACK,
    826 								TPF_6PT_GRAD | TPF_USE_GRAD_PAL | TPF_NOSHADOW);
    827 
    828 			//cancelbtn.Zap();
    829 			//buttons = &cancelbtn;
    830 
    831 			/*
    832 			.................... Rebuild the button list ....................
    833 			*/
    834 			//buttons->Draw_All();
    835 			cancelbtn.Draw_Me(true);
    836 
    837 			Show_Mouse();
    838 			display = false;
    839 		}
    840 
    841 
    842 
    843 		/*
    844 		** See if the game start packet has arrived from wchat yet.
    845 		*/
    846 		if (DDEServer.Get_MPlayer_Game_Info()){
    847 			//MessageBox (NULL, "About to restore focus to C&C95", "C&C95", MB_OK);
    848 			//SetForegroundWindow ( MainWindow );
    849 			//ShowWindow ( MainWindow, SW_SHOWMAXIMIZED	);
    850 			return(true);
    851 		}
    852 
    853 		//input = buttons->Input();
    854 		input = cancelbtn.Input();
    855 
    856 		/*
    857 		---------------------------- Process input ----------------------------
    858 		*/
    859 		switch (input) {
    860 
    861 			/*
    862 			** Cancel. Just return to the main menu
    863 			*/
    864 			case (KN_ESC):
    865 			case (BUTTON_CANCEL | KN_BUTTON):
    866 				process = false;
    867 				Send_Data_To_DDE_Server (packet, strlen(packet), DDEServerClass::DDE_CONNECTION_FAILED);
    868 				GameStatisticsPacketSent = false;
    869 				Spawn_WChat(false);
    870 				break;
    871 		}
    872 
    873 	}
    874 
    875 #endif	//DEMO
    876 
    877 	return (false);
    878 
    879 
    880 }
    881 
    882 
    883 
    884 
    885 
    886