Premium Реклама Spotlight Bundles Boost Банери Кредити
Основно Начало Сървъри Marketplace Форум Сървъри
Общности Хостинг Добави Auction Boost
Ресурси
Библиотеки Карти Видеа Магазин Bundles
Инструменти
Builder Demo CFG HUD
AMXX API
Вход Регистрация
TOP SERVER
[IG] Easy Surf | Ramp Fix | RANKS | REPLAYS
Counter-Strike 1.6
surf_flyin_fortress
40.160.19.36:27015
18.05 18:49
10/64
188ms
/ Библиотеки / server_query.inc

server_query.inc

listen

.inc 11.5 KB 415 реда 04.04.2026
Pawn / AMX Mod X
#if defined _server_query_included
	#endinput
#endif

#define _server_query_included

#if AMXX_VERSION_NUM >= 175
	#pragma reqlib server_query
	#if !defined AMXMODX_NOAUTOLOAD
		#pragma loadlib server_query
	#endif
#else
	#pragma library server_query
#endif

#include < amxmodx >

#define SQ_RULE_NAME_SIZE  256
#define SQ_RULE_VALUE_SIZE 256

/*
 * Queries a server for information
 * 
 * @param		ip - IP of the server without port
 * @param		port - The port number of the server
 * @param		type - The type of query to perform (matches SQ_* constants)
 * @param		function - The callback function to be executed when the query is finished
 * @param		error - The error code given when there was a problem with the query (matches SQError_* constants)
 * @param		timeout - The time in seconds to wait for a response before setting as failed
 * @param		data - Extra data array to pass to the callback function
 * @param		data_size - Size of the extra data array being passed
 * 
 * @note		Only 1 query can be performed on the same ip:port combination at a time.
 * 			Trying to use a different query type on the same ip:port while another is already taking place will throw an error.
 * 
 * @return		Returns unique SQuery ID (integer) on success, 0 on failure (and passes error code to param)
 * 
 * 
 * Structure for callback function:
 * 
 * sq_query("127.0.0.1", 27015, SQ_Server, "SQueryResults", errcode)
 * 
 * public SQueryResults(squery_id, type, Trie:buffer, Float:query_time, bool:failed, data[], data_size)
 * 
 * @param		squery_id - The unique SQuery ID (integer) return value from sq_query()
 * @param		type - The type of query performed (matches SQ_* constants)
 * @param		buffer - The buffer containing the server info
 * @param		query_time - The time in seconds it took for the query to finish
 * @param		failed - false if results were found, true otherwise
 * @param		data - The data sent to the sq_query() native
 * @param		data_size - The size of the data sent to the sq_query() native
 * 
 * @note		The buffer is a Trie with key->value pairs for data
 * 			Do not destroy this (or any Arrays or Tries it contains) in the callback!
 * 
 * @return		Return value is ignored
 * 
 */
enum _:ServerQueryType
{
	SQ_Server,
	SQ_Players,
	SQ_Challenge,
	SQ_Ping,
	SQ_Rules,
};
native sq_query(const ip[],const port,const type,const function[],&error,const timeout=60,const data[]="",const data_size=0);

/*
 * Gets a description of the errcode when sq_query() fails
 * 
 * @param		errcode - The error code from the sq_query() function (matches SQError_* constants)
 * @param		error - The output string to contain the description
 * @param		len - The max length of the result string
 * 
 * @return		The length of the result on success, 0 on failure
 * 
 */
enum _:ServerQueryErrors
{
	SQError_NoError,
	SQError_InvalidParams,
	SQError_MaxConnections,
	SQError_InvalidQueryType,
	SQError_InvalidIP,
	SQError_CouldNotConnect,
	SQError_InvalidFunction,
	SQError_AlreadyConnected
};
stock sq_error(const errcode,error[],const len)
{
	switch( errcode )
	{
		/*case SQError_NoError:
		{
			return copy( error, len, "No error" );
		}*/
		case SQError_InvalidParams:
		{
			return copy( error, len, "Invalid function parameter list." );
		}
		case SQError_MaxConnections:
		{
			return copy( error, len, "Too many server queries are already taking place." );
		}
		case SQError_InvalidQueryType:
		{
			return copy( error, len, "Invalid server query type." );
		}
		case SQError_InvalidIP:
		{
			return copy( error, len, "Invalid IP given." );
		}
		case SQError_CouldNotConnect:
		{
			return copy( error, len, "Could not connect to given IP." );
		}
		case SQError_InvalidFunction:
		{
			return copy( error, len, "Invalid function handle." );
		}
		case SQError_AlreadyConnected:
		{
			return copy( error, len, "Connection exists for given IP." );
		}
	}
	
	return 0;
}

/*
 * Gets a description of the server type based on it's servertype info from the buffer
 * 
 * @param		servertype - The servertype retrieved from the server info buffer (matches SERVERTYPE_* constants)
 * @param		result - The output string to contain the description
 * @param		len - The max length of the result string
 * 
 * @return		The length of the result on success, 0 on failure
 * 
 */
#define SERVERTYPE_LISTEN    'l' // listen
#define SERVERTYPE_DEDICATED 'd' // dedicated
#define SERVERTYPE_HLTV      'p' // HLTV
stock sq_servertype(const servertype,result[],const len)
{
	switch( servertype )
	{
		case SERVERTYPE_LISTEN:
		{
			return copy( result, len, "Listen" );
		}
		case SERVERTYPE_DEDICATED:
		{
			return copy( result, len, "Dedicated" );
		}
		case SERVERTYPE_HLTV:
		{
			return copy( result, len, "HLTV" );
		}
	}
	
	return 0;
}

/*
 * Converts the time played in the server into a descriptive string
 * 
 * @param		time_played - The time played
 * @param		output - The output string
 * @param		output_len - The max length of the output string
 * @param		steam_format (optional) - If true, it will be in the Steam format of "View Game Info" (eg. 1h 59m 13s, or 12m 4s). If false, it will be in HH:MM:SS format (default: false)
 * 
 * @return		The length of the output string
 * 
 */
stock sq_timeplayed(const Float:time_played,output[],const output_len,bool:steam_format=false)
{
	new iSeconds = floatround(time_played, floatround_floor);
	new iMinutes = iSeconds / 60;
	new iHours = iMinutes / 60;
	
	iSeconds %= 60;
	iMinutes %= 60;
	
	new iLen;
	
	if( steam_format )
	{
		if( iHours )
		{
			iLen = formatex( output, output_len, "%dh ", iHours );
		}
		
		if( iMinutes || iLen )
		{
			iLen += formatex( output[ iLen ], output_len - iLen, "%dm ", iMinutes );
		}
		
		if( iSeconds || iLen )
		{
			iLen += formatex( output[ iLen ], output_len - iLen, "%ds", iSeconds );
		}
	}
	else
	{
		iLen = formatex( output, output_len, "%d:%02d:%02d", iHours, iMinutes, iSeconds );
	}
	
	return iLen;
}

/*
 * Converts The Ship's response for game mode into a string
 * 
 * @param		game_mode - The game mode of the server
 * @param		output - The output string
 * @param		output_len - The max length of the output string
 * 
 * @return		The length of the output string on success, 0 on failure
 * 
 */
enum _:SHIP_GAMEMODES
{
	SHIP_GAMEMODE_HUNT,
	SHIP_GAMEMODE_ELIM,
	SHIP_GAMEMODE_DUEL,
	SHIP_GAMEMODE_DM,
	SHIP_GAMEMODE_TEAM_VIP,
	SHIP_GAMEMODE_TEAM_ELIM
};
stock sq_theship_gamemode(const game_mode,output[],const output_len)
{
	// 0x00 for Hunt, 0x01 for Elimination, 0x02 for Duel, 0x03 for Deathmatch, 0x04 for Team VIP, 0x05 for Team Elimination
	
	static const szGameModes[ SHIP_GAMEMODES ][ ] =
	{
		"Hunt",
		"Elimination",
		"Duel",
		"Deathmatch",
		"Team VIP",
		"Team Elimination"
	};
	
	return ( 0 <= game_mode < SHIP_GAMEMODES ) ? copy( output, output_len, szGameModes[ game_mode ] ) : 0;
}

/*
 * Reads a long from a buffer at a given start position
 * 
 * @param		buffer - The buffer to read from
 * @param		buffer_len - The length of the buffer
 * @param		start - The start position of the buffer
 * @param		result - The integer that is read is passed into that variable by reference
 * 
 * @return		Returns the end position in the buffer where the integer stops
 * 
 */
stock sq_readlong(const {Array,_}:buffer,const buffer_len,start,&result)
{
	return sq_readint( buffer, buffer_len, start, 4, result, true );
}

/*
 * Reads a short from a buffer at a given start position
 * 
 * @param		buffer - The buffer to read from
 * @param		buffer_len - The length of the buffer
 * @param		start - The start position of the buffer
 * @param		result - The integer that is read is passed into that variable by reference
 * 
 * @return		Returns the end position in the buffer where the integer stops
 * 
 */
stock sq_readshort(const {Array,_}:buffer,const buffer_len,start,&result)
{
	return sq_readint( buffer, buffer_len, start, 2, result, false );
}

/*
 * Reads a byte from a buffer at a given start position
 * 
 * @param		buffer - The buffer to read from
 * @param		buffer_len - The length of the buffer
 * @param		start - The start position of the buffer
 * @param		result - The integer that is read is passed into that variable by reference
 * 
 * @return		Returns the end position in the buffer where the integer stops
 * 
 */
stock sq_readbyte(const {Array,_}:buffer,const buffer_len,start,&result)
{
	return sq_readint( buffer, buffer_len, start, 1, result, false );
}

/*
 * Reads a float from a buffer at a given start position
 * 
 * @param		buffer - The buffer to read from
 * @param		buffer_len - The length of the buffer
 * @param		start - The start position of the buffer
 * @param		result - The float that is read is passed into that variable by reference
 * 
 * @return		Returns the end position in the buffer where the float stops
 * 
 */
stock sq_readfloat(const {Array,_}:buffer,const buffer_len,start,&Float:result)
{
	return sq_readint( buffer, buffer_len, start, 4, _:result, false );
}

/*
 * Reads an integer from a buffer at a given start position for a specific number of bytes
 * 
 * @param		buffer - The buffer to read from
 * @param		buffer_len - The length of the buffer
 * @param		start - The start position of the buffer
 * @param		bytes - The number of bytes to read
 * @param		result - The float that is read is passed into that variable by reference
 * @param		check_neg (optional) - If true, it checks if the integer is negative, otherwise it doesn't check (default: true)
 * 
 * @return		Returns the end position in the buffer where the integer stops
 * 
 */
stock sq_readint(const {Array,_}:buffer,const buffer_len,start,bytes,&result,bool:check_neg=true)
{
	result = 0;
	
	new iPos = start;
	
	if( ( iPos + bytes - 1 ) < buffer_len )
	{
		new bool:bNegative = ( check_neg && ArrayGetCell( Array:buffer, iPos + bytes - 1 ) < 0 );
		new iTemp;
		
		for( new i = 0; i < bytes; i++ )
		{
			result = sq_fixedunsigned8( ArrayGetCell( Array:buffer, iPos++ ) );
			
			if( bNegative )
			{
				result = 0xFF - result;
			}
			
			iTemp += ( result << ( 8 * i ) );
		}
		
		if( bNegative )
		{
			iTemp = ( iTemp + 1 ) * -1;
		}
		
		result = iTemp;
	}
	else
	{
		iPos += bytes;
	}
	
	return iPos;
}

/*
 * Reads a string from a buffer at given start position
 * 
 * @param		buffer - The buffer to read from
 * @param		buffer_len - The length of the buffer
 * @param		start - The start position of the buffer
 * @param		output - The output string
 * @param		output_len - The max length of the output string
 * 
 * @return		Returns the end position of where the string stops
 * 
 */
stock sq_readstring(const {Array,_}:buffer,const buffer_len,start,output[],const output_len)
{
	new iPos = start - 1;
	
	new cChar, iLen;
	while( ++iPos < buffer_len && ( cChar = ArrayGetCell( Array:buffer, iPos ) ) != 0 )
	{
		if( iLen < output_len )
		{
			output[ iLen++ ] = cChar;
		}
	}
	
	output[ iLen ] = 0;
	
	return ( iPos + 1 );
}

/*
 * Fixes a value to an unsigned 8-bit integer
 * 
 * @param		value - The value to be fixed
 * 
 * @return		Returns the fixed unsigned 8-bit integer
 * 
 */
stock sq_fixedunsigned8(value)
{
	value = clamp( value, -0xFF, 0xFF );
	
	if( value < 0 )
	{
		value = 0xFF + value + 1;
	}
	
	return value;
}
/* AMXX-Studio Notes - DO NOT MODIFY BELOW HERE
*{\\ rtf1\\ ansi\\ deff0{\\ fonttbl{\\ f0\\ fnil Tahoma;}}\n\\ viewkind4\\ uc1\\ pard\\ lang1033\\ f0\\ fs16 \n\\ par }
*/
РЕКЛАМИРАЙ ПРИ НАС!
AMXX-BG.INFO
КАК ДА ИЗПОЛЗВАМ
Добави в началото на .sma файла:
#include <server_query>
1. Изтегли
Свали файла от бутона по-горе
2. Копирай
Постави в scripting/include/
3. Включи
Добави #include директивата
4. Компилирай
Използвай amxxpc или scripting/compile.exe
PrivateServ.NET