Attempt to download missing files from the uri named by the local sv_dlURL setting, if specified, for easier demo playback.

git-svn-id: https://svn.code.sf.net/p/fteqw/code/trunk@6095 fc73d0e0-1445-4013-8a0c-d673dee63da5
This commit is contained in:
Spoike 2021-10-31 18:20:45 +00:00
parent d2937174bf
commit 3afbfc8547
5 changed files with 74 additions and 53 deletions

View File

@ -2331,7 +2331,7 @@ void CL_PakDownloads(int mode)
}
else
Q_strncpyz(local, pname, sizeof(local));
CL_CheckOrEnqueDownloadFile(pname, local, DLLF_NONGAME);
CL_CheckOrEnqueDownloadFile(pname, local, DLLF_ALLOWWEB|DLLF_NONGAME);
}
}
@ -4223,7 +4223,7 @@ static void CL_Curl_f(void)
int usage = 0;
qboolean alreadyhave = false;
extern char *cl_dp_packagenames;
unsigned int dlflags = DLLF_VERBOSE;
unsigned int dlflags = DLLF_VERBOSE|DLLF_ALLOWWEB;
if (argc < 2)
{
Con_Printf("%s: No args\n", Cmd_Argv(0));

View File

@ -548,8 +548,9 @@ qboolean CL_EnqueDownload(const char *filename, const char *localname, unsigned
downloadlist_t *dl;
qboolean webdl = false;
char ext[8];
if (!strncmp(filename, "http://", 7) || !strncmp(filename, "https://", 8))
if ((flags & DLLF_TRYWEB) || !strncmp(filename, "http://", 7) || !strncmp(filename, "https://", 8))
{
flags |= DLLF_TRYWEB;
if (!localname)
return false;
@ -715,7 +716,7 @@ static void CL_WebDownloadFinished(struct dl_download *dl)
else //other stuff is PROBABLY 403forbidden, but lets blame the server's config if its a tls issue etc.
CL_DownloadFailed(dl->url, &dl->qdownload, DLFAIL_SERVERCVAR);
if (dl->qdownload.flags & DLLF_ALLOWWEB) //re-enqueue it if allowed, but this time not from the web server.
CL_EnqueDownload(dl->qdownload.localname, dl->qdownload.localname, dl->qdownload.flags & ~DLLF_ALLOWWEB);
CL_EnqueDownload(dl->qdownload.localname, dl->qdownload.localname, dl->qdownload.flags & ~(DLLF_ALLOWWEB|DLLF_TRYWEB));
}
else if (dl->status == DL_FINISHED)
{
@ -737,7 +738,7 @@ static void CL_SendDownloadStartRequest(char *filename, char *localname, unsigne
return;
#ifdef WEBCLIENT
if (!strncmp(filename, "http://", 7) || !strncmp(filename, "https://", 8))
if (flags & DLLF_TRYWEB)
{
struct dl_download *wdl = HTTP_CL_Get(filename, localname, CL_WebDownloadFinished);
if (wdl)
@ -977,12 +978,20 @@ qboolean CL_CheckOrEnqueDownloadFile (const char *filename, const char *localnam
if (flags & DLLF_ALLOWWEB)
{
const char *sv_dlURL = InfoBuf_ValueForKey(&cl.serverinfo, "sv_dlURL");
flags &= ~DLLF_ALLOWWEB;
if (*sv_dlURL && (flags & DLLF_NONGAME) && !strncmp(filename, "package/", 8))
{
filename = va("%s/%s", cl_download_mapsrc.string, filename+8);
flags |= DLLF_ALLOWWEB;
extern cvar_t sv_dlURL;
const char *dlURL = InfoBuf_ValueForKey(&cl.serverinfo, "sv_dlURL");
if (!*dlURL)
dlURL = sv_dlURL.string;
flags &= ~(DLLF_TRYWEB|DLLF_ALLOWWEB);
if (*dlURL && (flags & DLLF_NONGAME) && !strncmp(filename, "package/", 8))
{ //filename is something like: package/GAMEDIR/foo.pk3
filename = va("%s/%s", dlURL, filename+8);
flags |= DLLF_TRYWEB|DLLF_ALLOWWEB;
}
else if (*dlURL)
{ //we don't really know which gamedir its meant to be for...
filename = va("%s/%s/%s", dlURL, FS_GetGamedir(true), filename);
flags |= DLLF_TRYWEB|DLLF_ALLOWWEB;
}
else if (*cl_download_mapsrc.string &&
!strcmp(filename, localname) &&
@ -991,11 +1000,16 @@ qboolean CL_CheckOrEnqueDownloadFile (const char *filename, const char *localnam
{
char base[MAX_QPATH];
COM_FileBase(filename, base, sizeof(base));
if (!strncmp(cl_download_mapsrc.string, "http://", 7) || !strncmp(cl_download_mapsrc.string, "https://", 8))
filename = va("%s%s.bsp", cl_download_mapsrc.string, base);
#ifndef FTE_TARGET_WEB
if (strncmp(cl_download_mapsrc.string, "http://", 7) && !strncmp(cl_download_mapsrc.string, "https://", 8))
{
Con_Printf("%s: Scheme not specified.\n", cl_download_mapsrc.name);
filename = va("https://%s/%s", cl_download_mapsrc.string, filename+5);
}
else
filename = va("http://%s/%s.bsp", cl_download_mapsrc.string, base);
flags |= DLLF_ALLOWWEB;
#endif
filename = va("%s%s", cl_download_mapsrc.string, filename+5);
flags |= DLLF_TRYWEB|DLLF_ALLOWWEB;
}
}
@ -1190,9 +1204,9 @@ static void Model_CheckDownloads (void)
continue;
Q_snprintfz(picname, sizeof(picname), "pics/%s.pcx", cl.image_name[i]);
if (!strncmp(cl.image_name[i], "../", 3)) //some servers are just awkward.
CL_CheckOrEnqueDownloadFile(picname, picname+8, 0);
CL_CheckOrEnqueDownloadFile(picname, picname+8, DLLF_ALLOWWEB);
else
CL_CheckOrEnqueDownloadFile(picname, picname, 0);
CL_CheckOrEnqueDownloadFile(picname, picname, DLLF_ALLOWWEB);
}
if (!CLQ2_RegisterTEntModels())
return;
@ -1213,7 +1227,7 @@ static void Model_CheckDownloads (void)
continue;
#endif
CL_CheckOrEnqueDownloadFile(s, s, (i==1)?DLLF_REQUIRED|DLLF_ALLOWWEB:0); //world is required to be loaded.
CL_CheckOrEnqueDownloadFile(s, s, ((i==1)?DLLF_REQUIRED:0)|DLLF_ALLOWWEB); //world is required to be loaded.
CL_CheckModelResources(s);
}
@ -1228,7 +1242,7 @@ static void Model_CheckDownloads (void)
if (!*s)
continue;
CL_CheckOrEnqueDownloadFile(s, s, 0);
CL_CheckOrEnqueDownloadFile(s, s, DLLF_ALLOWWEB);
CL_CheckModelResources(s);
}
#endif
@ -1576,7 +1590,7 @@ void Sound_CheckDownload(const char *s)
return;
#endif
//download the one the server said.
CL_CheckOrEnqueDownloadFile(s, NULL, 0);
CL_CheckOrEnqueDownloadFile(s, NULL, DLLF_ALLOWWEB);
}
/*
@ -1639,6 +1653,7 @@ void CL_RequestNextDownload (void)
/*request downloads only if we're at the point where we've received a complete list of them*/
if (cl.sendprespawn || cls.state == ca_active)
{
if (cl.downloadlist)
{
downloadlist_t *dl;
@ -1663,7 +1678,7 @@ void CL_RequestNextDownload (void)
fl = dl->flags;
/*if we don't require downloads don't queue requests until we're actually on the server, slightly more deterministic*/
if (cls.state == ca_active || (requiredownloads.value && !cls.demoplayback) || (fl & DLLF_REQUIRED))
if (cls.state == ca_active || (requiredownloads.value && !(cls.demoplayback && !(fl&DLLF_TRYWEB))) || (fl & DLLF_REQUIRED))
{
if ((fl & DLLF_OVERWRITE) || !CL_CheckFile (dl->localname))
{
@ -1682,6 +1697,9 @@ void CL_RequestNextDownload (void)
}
}
}
else if (cls.download && requiredownloads.value)
return;
}
if (cl.sendprespawn)
{ // get next signon phase
@ -4402,7 +4420,7 @@ static void CL_ParseModellist (qboolean lots)
SCR_SetLoadingFile("loading data");
//we need to try to load it now if we can, so any embedded archive will be loaded *before* we start looking for other content...
cl.model_precache[1] = Mod_ForName (cl.model_name[1], MLV_WARNSYNC);
cl.model_precache[1] = Mod_ForName (cl.model_name[1], MLV_SILENT);
if (cl.model_precache[1] && cl.model_precache[1]->loadstate == MLS_LOADED)
FS_LoadMapPackFile(cl.model_precache[1]->name, cl.model_precache[1]->archive);
@ -6788,7 +6806,7 @@ static void CL_ParsePrecache(void)
if (i >= 1 && i < MAX_PRECACHE_MODELS)
{
model_t *model;
CL_CheckOrEnqueDownloadFile(s, s, 0);
CL_CheckOrEnqueDownloadFile(s, s, DLLF_ALLOWWEB);
model = Mod_ForName(Mod_FixName(s, cl.model_name[1]), (i == 1)?MLV_ERROR:MLV_WARN);
// if (!model)
// Con_Printf("svc_precache: Mod_ForName(\"%s\") failed\n", s);
@ -6807,7 +6825,7 @@ static void CL_ParsePrecache(void)
{
sfx_t *sfx;
if (S_HaveOutput())
CL_CheckOrEnqueDownloadFile(va("sound/%s", s), NULL, 0);
CL_CheckOrEnqueDownloadFile(va("sound/%s", s), NULL, DLLF_ALLOWWEB);
sfx = S_PrecacheSound (s);
// if (!sfx)
// Con_Printf("svc_precache: S_PrecacheSound(\"%s\") failed\n", s);

View File

@ -576,6 +576,7 @@ typedef struct downloadlist_s {
#define DLLF_BEGUN (1u<<8) //server has confirmed that the file exists, is readable, and we've opened a file. should not be set on new requests.
#define DLLF_ALLOWWEB (1u<<9) //failed http downloads should retry but from the game server itself
#define DLLF_TRYWEB (1u<<10) //should be trying to download it from a website...
enum dlfailreason_e failreason;
struct downloadlist_s *next;

View File

@ -78,7 +78,11 @@ extern cvar_t password;
#endif
cvar_t spectator_password = CVARF("spectator_password", "", CVAR_NOUNSAFEEXPAND); // password for entering as a sepctator
#ifdef FTE_TARGET_WEB
cvar_t sv_dlURL = CVARAFD(/*ioq3*/"sv_dlURL", "", /*dp*/"sv_curl_defaulturl", CVAR_SERVERINFO|CVAR_NOSAVE, "Provides clients with an external url from which they can obtain pk3s/packages from an external http server instead of having to download over udp.");
#else
cvar_t sv_dlURL = CVARAFD(/*ioq3*/"sv_dlURL", "", /*dp*/"sv_curl_defaulturl", CVAR_SERVERINFO|CVAR_ARCHIVE, "Provides clients with an external url from which they can obtain pk3s/packages from an external http server instead of having to download over udp.");
#endif
cvar_t allow_download = CVARAD("allow_download", "1", /*q3*/"sv_allowDownload", "If 1, permits downloading. Set to 0 to unconditionally block *ALL* downloads from this server. You may wish to set sv_dlURL if you wish clients to still be able to download content.");
cvar_t allow_download_skins = CVARD("allow_download_skins", "1", "0 blocks downloading of any file in the skins/ directory");
cvar_t allow_download_models = CVARD("allow_download_models", "1", "0 blocks downloading of any file in the progs/ or models/ directory");

View File

@ -789,13 +789,11 @@ mergeInto(LibraryManager.library,
};
var dcconfig = {ordered: false, maxRetransmits: 0, reliable:false};
console.log("emscriptenfte_rtc_create");
var s = {pc:null, ws:null, inq:[], err:0, con:0, isclient:clientside, callcb:
function(evtype,stringdata)
{ //private helper
console.log("emscriptenfte_rtc_create callback: " + evtype);
//console.log("emscriptenfte_rtc_create callback: " + evtype);
var stringlen = (stringdata.length*3)+1;
var dataptr = _malloc(stringlen);
@ -823,15 +821,15 @@ console.log("emscriptenfte_rtc_create callback: " + evtype);
s.ws.binaryType = 'arraybuffer';
s.ws.onclose = function(event)
{
console.log("webrtc datachannel closed:")
console.log(event);
//console.log("webrtc datachannel closed:")
//console.log(event);
s.con = 0;
s.err = 1;
};
s.ws.onopen = function(event)
{
console.log("webrtc datachannel opened:");
console.log(event);
//console.log("webrtc datachannel opened:");
//console.log(event);
s.con = 1;
};
s.ws.onmessage = function(event)
@ -844,8 +842,8 @@ console.log(event);
s.pc.onicecandidate = function(e)
{
console.log("onicecandidate: ");
console.log(e);
//console.log("onicecandidate: ");
//console.log(e);
var desc;
if (1)
desc = JSON.stringify(e.candidate);
@ -855,18 +853,18 @@ console.log(e);
};
s.pc.oniceconnectionstatechange = function(e)
{
console.log("oniceconnectionstatechange: ");
console.log(e);
//console.log("oniceconnectionstatechange: ");
//console.log(e);
};
s.pc.onaddstream = function(e)
{
console.log("onaddstream: ");
console.log(e);
//console.log("onaddstream: ");
//console.log(e);
};
s.pc.ondatachannel = function(e)
{
console.log("ondatachannel: ");
console.log(e);
//console.log("ondatachannel: ");
//console.log(e);
s.recvchan = e.channel;
s.recvchan.binaryType = 'arraybuffer';
@ -875,8 +873,8 @@ console.log(e);
};
s.pc.onnegotiationneeded = function(e)
{
console.log("onnegotiationneeded: ");
console.log(e);
//console.log("onnegotiationneeded: ");
//console.log(e);
};
if (clientside)
@ -885,8 +883,8 @@ console.log(e);
function(desc)
{
s.pc.setLocalDescription(desc);
console.log("gotlocaldescription: ");
console.log(desc);
// console.log("gotlocaldescription: ");
// console.log(desc);
if (1)
desc = JSON.stringify(desc);
@ -897,8 +895,8 @@ console.log(e);
},
function(event)
{
console.log("createOffer error:");
console.log(event);
// console.log("createOffer error:");
// console.log(event);
s.err = 1;
}
);
@ -930,8 +928,8 @@ console.log(e);
function(desc)
{
s.pc.setLocalDescription(desc);
console.log("gotlocaldescription: ");
console.log(desc);
// console.log("gotlocaldescription: ");
// console.log(desc);
if (1)
desc = JSON.stringify(desc);
@ -942,7 +940,7 @@ console.log(e);
},
function(event)
{
console.log("createAnswer error:" + event.toString());
// console.log("createAnswer error:" + event.toString());
s.err = 1;
}
);
@ -962,8 +960,8 @@ console.log(e);
desc = JSON.parse(offer);
else
desc = {candidate:offer, sdpMid:null, sdpMLineIndex:0};
console.log("addIceCandidate:");
console.log(desc);
//console.log("addIceCandidate:");
//console.log(desc);
s.pc.addIceCandidate(desc);
} catch(err) { console.log(err); }
},
@ -971,7 +969,7 @@ console.log(desc);
emscriptenfte_async_wget_data2 : function(url, ctx, onload, onerror, onprogress)
{
var _url = UTF8ToString(url);
console.log("Attempting download of " + _url);
// console.log("Attempting download of " + _url);
var http = new XMLHttpRequest();
try
{
@ -987,7 +985,7 @@ console.log(desc);
http.onload = function(e)
{
console.log("onload: " + _url + " status " + http.status);
//console.log("onload: " + _url + " status " + http.status);
if (http.status == 200)
{
if (onload)
@ -1002,7 +1000,7 @@ console.log("onload: " + _url + " status " + http.status);
http.onerror = function(e)
{
console.log("onerror: " + _url);
//console.log("onerror: " + _url);
if (onerror)
{{{makeDynCall('vii')}}}(onerror, ctx, 0);
};