예제 #1
0
/*
=======================================================================================================================================
DL_BeginDownload

Inspired from http://www.w3.org/Library/Examples/LoadToFile.c, setup the download, return once we have a connection.
=======================================================================================================================================
*/
int DL_BeginDownload(char *localName, const char *remoteName) {
	char referer[MAX_STRING_CHARS + 5 /*"ET://"*/];

	if (dl_request) {
		Com_Printf(S_COLOR_RED "DL_BeginDownload: Error - called with a download request already active\n");
		return 0;
	}

	if (!localName[0] || !remoteName[0]) {
		Com_Printf(S_COLOR_RED "DL_BeginDownload: Error - empty download URL or empty local file name\n");
		return 0;
	}

	if (FS_CreatePath(localName)) {
		Com_Printf(S_COLOR_RED "DL_BeginDownload: Error - unable to create directory(%s).\n", localName);
		return 0;
	}

	dl_file = fopen(localName, "wb + ");

	if (!dl_file) {
		Com_Printf(S_COLOR_RED  "DL_BeginDownload: Error - unable to open '%s' for writing\n", localName);
		return 0;
	}

	DL_InitDownload();
	// ET://ip:port
	strcpy(referer, "ET://");
	Q_strncpyz(referer + 5, Cvar_VariableString("cl_currentServerIP"), MAX_STRING_CHARS);

	dl_request = curl_easy_init();
	curl_easy_setopt(dl_request, CURLOPT_USERAGENT, va("%s %s", APP_NAME "/" APP_VERSION, curl_version()));
	curl_easy_setopt(dl_request, CURLOPT_REFERER, referer);
	curl_easy_setopt(dl_request, CURLOPT_URL, remoteName);
	curl_easy_setopt(dl_request, CURLOPT_WRITEFUNCTION, DL_cb_FWriteFile);
	curl_easy_setopt(dl_request, CURLOPT_WRITEDATA, (void *)dl_file);
	curl_easy_setopt(dl_request, CURLOPT_PROGRESSFUNCTION, DL_cb_Progress);
	curl_easy_setopt(dl_request, CURLOPT_NOPROGRESS, 0);
	curl_easy_setopt(dl_request, CURLOPT_FAILONERROR, 1);
	curl_easy_setopt(dl_request, CURLOPT_FOLLOWLOCATION, 1);
	curl_easy_setopt(dl_request, CURLOPT_MAXREDIRS, 5);
#ifdef FEATURE_OPENSSL
#if 0
	curl_easy_setopt(dl_request, CURLOPT_CAINFO, "./cert.crt");
#else
	curl_easy_setopt(dl_request, CURLOPT_SSL_VERIFYHOST, 0);
	curl_easy_setopt(dl_request, CURLOPT_SSL_VERIFYPEER, 0);
#endif
#endif
	if (curl_multi_add_handle(dl_multi, dl_request) != CURLM_OK) {
		Com_Printf(S_COLOR_RED "DL_BeginDownload: Error - invalid handle.\n");
	}

	Cvar_Set("cl_downloadName", remoteName);

	return 1;
}
예제 #2
0
/*
===============
inspired from http://www.w3.org/Library/Examples/LoadToFile.c
setup the download, return once we have a connection
===============
*/
int DL_BeginDownload( const char *localName, const char *remoteName, int debug )
{
	char referer[ MAX_STRING_CHARS + URI_SCHEME_LENGTH ];

	if ( dl_request )
	{
		curl_multi_remove_handle( dl_multi, dl_request );
		curl_easy_cleanup( dl_request );
		dl_request = NULL;
	}

	if ( dl_file )
	{
		FS_FCloseFile( dl_file );
		dl_file = 0;
	}

	if ( !localName || !remoteName )
	{
		Com_DPrintf( "Empty download URL or empty local file name\n" );
		return 0;
	}

	dl_file = FS_SV_FOpenFileWrite( localName );

	if ( !dl_file )
	{
		Com_Printf( "ERROR: DL_BeginDownload unable to open '%s' for writing\n", localName );
		return 0;
	}

	DL_InitDownload();

	strcpy( referer, URI_SCHEME );
	Q_strncpyz( referer + URI_SCHEME_LENGTH, Cvar_VariableString( "cl_currentServerIP" ), MAX_STRING_CHARS );

	dl_request = curl_easy_init();
	curl_easy_setopt( dl_request, CURLOPT_USERAGENT, va( "%s %s", PRODUCT_NAME "/" PRODUCT_VERSION, curl_version() ) );
	curl_easy_setopt( dl_request, CURLOPT_REFERER, referer );
	curl_easy_setopt( dl_request, CURLOPT_URL, remoteName );
	curl_easy_setopt( dl_request, CURLOPT_WRITEFUNCTION, DL_cb_FWriteFile );
	curl_easy_setopt( dl_request, CURLOPT_WRITEDATA, ( void * )( intptr_t ) dl_file );
	curl_easy_setopt( dl_request, CURLOPT_PROGRESSFUNCTION, DL_cb_Progress );
	curl_easy_setopt( dl_request, CURLOPT_NOPROGRESS, 0 );
	curl_easy_setopt( dl_request, CURLOPT_FAILONERROR, 1 );

	curl_multi_add_handle( dl_multi, dl_request );

	Cvar_Set( "cl_downloadName", remoteName );

	return 1;
}
예제 #3
0
/*
===============
inspired from http://www.w3.org/Library/Examples/LoadToFile.c
setup the download, return once we have a connection
===============
*/
int DL_BeginDownload(const char *localName, const char *remoteName, int debug)
{
	char            referer[MAX_STRING_CHARS + 5 /*"ET://" */ ];

	if(dl_request)
	{
		Com_Printf("ERROR: DL_BeginDownload called with a download request already active\n");
		return 0;
	}

	if(!localName || !remoteName)
	{
		Com_DPrintf("Empty download URL or empty local file name\n");
		return 0;
	}

	FS_CreatePath(localName);
	dl_file = fopen(localName, "wb+");
	if(!dl_file)
	{
		Com_Printf("ERROR: DL_BeginDownload unable to open '%s' for writing\n", localName);
		return 0;
	}

	DL_InitDownload();

	/* ET://ip:port */
	strcpy(referer, "ET://");
	Q_strncpyz(referer + 5, Cvar_VariableString("cl_currentServerIP"), MAX_STRING_CHARS);

	dl_request = curl_easy_init();
	curl_easy_setopt(dl_request, CURLOPT_USERAGENT, va("%s %s", APP_NAME "/" APP_VERSION, curl_version()));
	curl_easy_setopt(dl_request, CURLOPT_REFERER, referer);
	curl_easy_setopt(dl_request, CURLOPT_URL, remoteName);
	curl_easy_setopt(dl_request, CURLOPT_WRITEFUNCTION, DL_cb_FWriteFile);
	curl_easy_setopt(dl_request, CURLOPT_WRITEDATA, (void *)dl_file);
	curl_easy_setopt(dl_request, CURLOPT_PROGRESSFUNCTION, DL_cb_Progress);
	curl_easy_setopt(dl_request, CURLOPT_NOPROGRESS, 0);
	curl_easy_setopt(dl_request, CURLOPT_FAILONERROR, 1);

	curl_multi_add_handle(dl_multi, dl_request);

	Cvar_Set("cl_downloadName", remoteName);

	return 1;
}
예제 #4
0
/*
===============
inspired from http://www.w3.org/Library/Examples/LoadToFile.c
setup the download, return once we have a connection
===============
*/
int DL_BeginDownload( const char *localName, const char *remoteName, int debug )
{
	char *access = NULL;
	char *url = NULL;
	char *login = NULL;
	char *path = NULL;
	char *ptr = NULL;

	if ( dl_running )
	{
		Com_Printf(_( "ERROR: DL_BeginDownload called with a download request already active\n" ));
		return 0;
	}

	terminate_status = HT_UNDEF;

#ifdef HTDEBUG

	if ( debug )
	{
		WWWTRACE = SHOW_ALL_TRACE;
	}

#endif

	if ( !localName || !remoteName )
	{
		Com_DPrintf( "Empty download URL or empty local file name\n" );
		return 0;
	}

	DL_InitDownload();

	/* need access for ftp behaviour and HTTP Basic Auth */
	access = HTParse( remoteName, "", PARSE_ACCESS );

	/*
	   Set the timeout for how long we are going to wait for a response
	   This needs to be set and reset to 0 after dl each time
	   idcvs/2003-January/000449.html
	   http://lists.w3.org/Archives/Public/www-lib/2003AprJun/0033.html
	   In case of ftp download, we leave no timeout during connect phase cause of libwww bugs
	   show_bug.cgi?id=605
	 */
	if ( !Q_stricmp( access, "ftp" ) )
	{
		dl_is_ftp = 1;
		HTHost_setEventTimeout( -1 );
	}
	else
	{
		dl_is_ftp = 0;
		HTHost_setEventTimeout( 30000 );
	}

	dl_request = HTRequest_new();

	/* HTTP Basic Auth */
	if ( !Q_stricmp( access, "http" ) )
	{
		HTBasic *basic;

		login = HTParse( remoteName, "", PARSE_HOST );
		path = HTParse( remoteName, "", PARSE_PATH + PARSE_PUNCTUATION );
		ptr = strchr( login, '@' );

		if ( ptr )
		{
			/* Uid and/or passwd specified */
			char *passwd;

			*ptr = '\0';
			passwd = strchr( login, ':' );

			if ( passwd )
			{
				/* Passwd specified */
				*passwd++ = '\0';
				HTUnEscape( passwd );
			}

			HTUnEscape( login );
			/* proactively set the auth */
			basic = HTBasic_new();
			StrAllocCopy( basic->uid, login );
			StrAllocCopy( basic->pw, passwd );
			basic_credentials( dl_request, basic );
			HTBasic_delete( basic );
			/* correct the HTTP */
			url = HT_MALLOC( 7 + strlen( ptr + 1 ) + strlen( path ) + 1 );
			sprintf( url, "http://%s%s", ptr + 1, path );
			Com_DPrintf( "HTTP Basic Auth – %s %s %s\n", login, passwd, url );
			HT_FREE( login );
			HT_FREE( path );
		}
		else
		{
			StrAllocCopy( url, remoteName );
		}
	}
	else
	{
		StrAllocCopy( url, remoteName );
	}

	HT_FREE( access );

	FS_CreatePath( localName );

	/* Start the load */
	if ( HTLoadToFile( url, dl_request, localName ) != YES )
	{
		Com_DPrintf( "HTLoadToFile failed\n" );
		HT_FREE( url );
		HTProfile_delete();
		return 0;
	}

	HT_FREE( url );

	/* remove possible login/pass part for the ui */
	access = HTParse( remoteName, "", PARSE_ACCESS );
	login = HTParse( remoteName, "", PARSE_HOST );
	path = HTParse( remoteName, "", PARSE_PATH + PARSE_PUNCTUATION );
	ptr = strchr( login, '@' );

	if ( ptr )
	{
		/* Uid and/or passwd specified */
		Cvar_Set( "cl_downloadName", va( "%s://*:*%s%s", access, ptr, path ) );
	}
	else
	{
		Cvar_Set( "cl_downloadName", remoteName );
	}

	HT_FREE( path );
	HT_FREE( login );
	HT_FREE( access );

	if ( dl_is_ftp )
	{
		HTHost_setEventTimeout( 30000 );
	}

	/* Go into the event loop... */
	HTEventList_init( dl_request );

	dl_running = 1;

	return 1;
}
예제 #5
0
char *DL_GetString(const char *url)
{
	CURL     *curl = NULL;
	CURLcode status;
	char     *data = NULL;
	long     code;

	write_result_t write_result = { NULL, 0 };

	if (!url)
	{
		Com_Printf("Empty download URL\n");
		return NULL;
	}

	DL_InitDownload();

	curl = curl_easy_init();

	data = (char *)malloc(GET_BUFFER_SIZE);
	if (!data)
	{
		goto error_get;
	}
	else
	{
		write_result.data = data;
	}

	curl_easy_setopt(curl, CURLOPT_USERAGENT, va("%s %s", APP_NAME "/" APP_VERSION, curl_version()));
	curl_easy_setopt(curl, CURLOPT_URL, url);
	curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
	curl_easy_setopt(curl, CURLOPT_SSL_VERIFYPEER, 0L);
	curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, DL_write_function);
	curl_easy_setopt(curl, CURLOPT_WRITEDATA, &write_result);

	status = curl_easy_perform(curl);
	if (status != 0)
	{
		Com_Printf("DL_GetString unable to request data from %s\n", url);
		Com_Printf("DL_GetString %s\n", curl_easy_strerror(status));
		goto error_get;
	}

	curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &code);
	if (code != 200)
	{
		Com_Printf("DL_GetString server responded with code %ld\n", code);
		goto error_get;
	}

	curl_easy_cleanup(curl);
	data[write_result.pos] = '\0';

	return data;

error_get:

	if (curl)
	{
		curl_easy_cleanup(curl);
	}

	if (data)
	{
		free(data);
	}

	return NULL;
}
예제 #6
0
/*
=======================================================================================================================================
DL_GetString
=======================================================================================================================================
*/
char *DL_GetString(const char *url) {
	CURL *curl = NULL;
	CURLcode status;
	char *data = NULL;
	long code;

	write_result_t write_result = {NULL, 0};

	if (!url) {
		Com_Printf(S_COLOR_RED "DL_GetString: Error - empty download URL\n");
		return NULL;
	}

	DL_InitDownload();

	curl = curl_easy_init();
	data = (char *)Com_Allocate(GET_BUFFER_SIZE);

	if (!data) {
		goto error_get;
	} else {
		write_result.data = data;
	}

	curl_easy_setopt(curl, CURLOPT_USERAGENT, va("%s %s", APP_NAME "/" APP_VERSION, curl_version()));
	curl_easy_setopt(curl, CURLOPT_URL, url);
	curl_easy_setopt(curl, CURLOPT_FOLLOWLOCATION, 1L);
	curl_easy_setopt(curl, CURLOPT_WRITEFUNCTION, DL_write_function);
	curl_easy_setopt(curl, CURLOPT_WRITEDATA, (void *)&write_result);
#ifdef FEATURE_OPENSSL
#if 0
	curl_easy_setopt(dl_request, CURLOPT_CAINFO, "./cert.crt");
#else
	curl_easy_setopt(dl_request, CURLOPT_SSL_VERIFYHOST, 0);
	curl_easy_setopt(dl_request, CURLOPT_SSL_VERIFYPEER, 0);
#endif
#endif
	status = curl_easy_perform(curl);

	if (status != 0) {
		Com_Printf(S_COLOR_RED "DL_GetString: Error - unable to request data from %s\n", url);
		Com_Printf(S_COLOR_RED "DL_GetString: Error - %s\n", curl_easy_strerror(status));
		goto error_get;
	}

	curl_easy_getinfo(curl, CURLINFO_RESPONSE_CODE, &code);

	if (code != 200) {
		Com_Printf(S_COLOR_RED "DL_GetString: Error - server responded with code %ld\n", code);
		goto error_get;
	}

	curl_easy_cleanup(curl);
	data[write_result.pos] = '\0';

	return data;

error_get:
	if (curl) {
		curl_easy_cleanup(curl);
	}

	if (data) {
		Com_Dealloc(data);
	}

	return NULL;
}