gamespy server list

Network protocols, internals and low-level information about games
dex123
Posts: 3
Joined: Thu Nov 26, 2015 11:08 am

gamespy server list

Post by dex123 »

Hi, i am trying to get list of servers from master server
game: serious sam classic the second encounter
master: gs.ostap.eu
port: 28900

but i cant get ips from last packet. How i can decrypt this? :

Code: Select all

w}hGHEa+@:?.mep,y9Pxb.m].mN.mN.mR.mZ=.mi.mN5.mRY.mR.m^.mb5.mi*&Vd.mN?.mO.mO9.mR.mR.mY.mZQ.ma.mV.md*&Vd?>P.mN+.mN.mO%.mOa.mR.mR.mR.mR.mR.mV.mZ.mZy.m^.m^H.m..mb.mbg.mV.mj7d*&Vdl=dNk#d?>T>Jd>Jd\final\


InGame Browser gets it too in same view [wireshark screen]:
Image

cpp code I have tried:
[spoiler=123]

Code: Select all

#include <iostream>
#include "gsmsalg.h"

#include <winsock2.h>
#include <windows.h>

using namespace std;

#pragma comment(lib, "ws2_32.lib")



#define PORT 28900
#define SERVERADDR "46.165.228.109" //Звёздочками пометил свой IP

//65.112.87.186
//46.165.228.109

int main()
{
    char buff[1024];
 
    // Шаг 1 - инициализация библиотеки Winsock
    if (WSAStartup(0x202, (WSADATA *)&buff[0]))
    {
        printf("WSAStart error %d\n", WSAGetLastError());
        return -1;
    }
 
    // Шаг 2 - создание сокета
    SOCKET my_sock;
    my_sock = socket(AF_INET, SOCK_STREAM, 0);
    if (my_sock < 0)
    {
        printf("Socket() error %d\n", WSAGetLastError());
        return -1;
    }
 
    // Шаг 3 - установка соединения
    // заполнение структуры sockaddr_in - указание адреса и порта сервера
    sockaddr_in dest_addr;
    dest_addr.sin_family = AF_INET;
    dest_addr.sin_port = htons(PORT);
    HOSTENT *hst;
 
    // преобразование IP адреса из символьного в сетевой формат
    if (inet_addr(SERVERADDR) != INADDR_NONE)
        dest_addr.sin_addr.s_addr = inet_addr(SERVERADDR);
    else
    {
        // попытка получить IP адрес по доменному имени сервера
        if (hst = gethostbyname(SERVERADDR))
            // hst->h_addr_list содержит не массив адресов,
            // а массив указателей на адреса
            ((unsigned long *)&dest_addr.sin_addr)[0] =
            ((unsigned long **)hst->h_addr_list)[0][0];
        else
        {
            printf("Invalid address %s\n", SERVERADDR);
            closesocket(my_sock);
            WSACleanup();
            return -1;
        }
    }
 
    // адрес сервера получен - пытаемся установить соединение
    if (connect(my_sock, (sockaddr *)&dest_addr, sizeof(dest_addr)))
    {
        printf("Connect error %d\n", WSAGetLastError());
        return -1;
    }
 
    printf("OK.\n\n", SERVERADDR);
 
   char buffer[64];
    // Шаг 4 - чтение и передача сообщений
    int nsize;
nsize = recv(my_sock, &buff[0], sizeof(buff) - 1, 0);
        // ставим завершающий ноль в конце строки
        buff[nsize] = 0;
 
      strcpy_s(buffer, &buff[15]);

      printf("%s\n", buffer);

      unsigned char  *dest;

      unsigned char* y ;
      y = (unsigned char*) buffer;

      const char* q = "AKbna4";
      unsigned char* w ;
      w = (unsigned char*) q;

      dest = gsseckey( NULL, y, w, 0);
      std::cout << dest << std::endl;

        // выводим на экран
        printf("%s", buff);
 


      char sss[256];
      strcpy_s( sss, "\\gamename\\serioussamse\\gamever\\1.6\\location\\0\\validate\\" );

      char * destchar;
      destchar = (char *) dest;
      strcat_s( sss, destchar);
      strcat_s( sss, "\\final\\\\queryid\\1.1\\");
      
      cout << endl << "sss=" << sss ;
        // читаем пользовательский ввод с клавиатуры
       // printf("\nyou:"); fgets(&buff[0], sizeof(buff) - 1, stdin);

      send(my_sock, sss, strlen(sss), 0);

      char query[64] = "\\list\\cmp\\gamename\\serioussamse\\final\\";
      send(my_sock, query, strlen(query), 0);

      recv(my_sock, &buff[0], sizeof(buff) - 1, 0);

      printf("\n%s\n", buff);

      cout << endl << buff[0] << endl;
        // передаем строку клиента серверу
       
   
    printf("Recv error %d\n", WSAGetLastError());
    closesocket(my_sock);
    WSACleanup();

   system("pause");
   return 0;
}

[/spoiler]
aluigi
Site Admin
Posts: 12984
Joined: Wed Jul 30, 2014 9:32 pm

Re: gamespy server list

Post by aluigi »

Port 28900 is used for encrypted queries (enctype 1, 2 and X), 28910 for plain-text.
If you need a client example (for wireshark because the code is not simple) check gslist: http://aluigi.altervista.org/papers.htm#gslist
If you want to "play" with encryption and need a minimalistic code as test and example:
http://aluigi.org/papers/enctypedec.zip

This stuff has been discussed a lot also on my old forum so check there too with google:
"enctype" site:aluigi.freeforums.org
dex123
Posts: 3
Joined: Thu Nov 26, 2015 11:08 am

Re: gamespy server list

Post by dex123 »

zomg, enctype1 is just 4 bytes and 1 short like Valve master server responce. I should have known :mrgreen: thx
aluigi
Site Admin
Posts: 12984
Joined: Wed Jul 30, 2014 9:32 pm

Re: gamespy server list

Post by aluigi »

A note regarding using gslist with the unofficial Gamespy servers, it's necessary to specify the key of the requested game.
Example for qtracker:

Code: Select all

gslist -n ironstorm -Y ironstorm y5Ei7C -x 65.112.87.186