Esempio n. 1
0
void RP_SDPFromFile(RTPClient *rtp, char *file_name, RTPStream *stream)
{
	FILE *_sdp;
	char *sdp_buf;
	u32 sdp_size;

	sdp_buf = NULL;

	if (file_name && strstr(file_name, "file://")) file_name += strlen("file://");
	if (!file_name || !(_sdp = gf_fopen(file_name, "rt")) ) {
		gf_service_connect_ack(rtp->service, NULL, GF_URL_ERROR);
		return;
	}

	gf_fseek(_sdp, 0, SEEK_END);
	sdp_size = (u32) gf_ftell(_sdp);
	gf_fseek(_sdp, 0, SEEK_SET);
	sdp_buf = (char*)gf_malloc(sdp_size);
	if (1 > fread(sdp_buf, 1, sdp_size, _sdp)) {
		gf_service_connect_ack(rtp->service, NULL, GF_URL_ERROR);
	} else {
		RP_LoadSDP(rtp, sdp_buf, sdp_size, stream);
	}
	gf_fclose(_sdp);
	gf_free(sdp_buf);
}
Esempio n. 2
0
GF_Err LIBPLAYER_ConnectChannel(GF_InputService *plug, LPNETCHANNEL channel, const char *url, Bool upstream)
{
	u32 ESID;
	LibPlayerIn *read = (LibPlayerIn *) plug->priv;
	sscanf(url, "ES_ID=%ud", &ESID);
	GF_LOG(GF_LOG_DEBUG, GF_LOG_MODULE, ("[LibPlayerIN] instance %d connect channel %d\n", read->player_id, ESID));
	if (ESID != 1+read->player_id) {
		gf_service_connect_ack(read->service, channel, GF_STREAM_NOT_FOUND);
	} else {
		gf_service_connect_ack(read->service, channel, GF_OK);
	}
	return GF_OK;
}
Esempio n. 3
0
static GF_Err AC3_ConnectService(GF_InputService *plug, GF_ClientService *serv, const char *url)
{
	char szURL[2048];
	char *ext;
	GF_Err reply;
	AC3Reader *read = plug->priv;
	read->service = serv;

	if (read->dnload) gf_service_download_del(read->dnload);
	read->dnload = NULL;

	strcpy(szURL, url);
	ext = strrchr(szURL, '#');
	if (ext) ext[0] = 0;

	/*remote fetch*/
	read->is_remote = !ac3_is_local(szURL);
	if (read->is_remote) {
		ac3_download_file(plug, (char *) szURL);
		return GF_OK;
	}

	reply = GF_OK;
	read->stream = gf_f64_open(szURL, "rb");
	if (!read->stream) {
		reply = GF_URL_ERROR;
	} else if (!AC3_ConfigureFromFile(read)) {
		fclose(read->stream);
		read->stream = NULL;
		reply = GF_NOT_SUPPORTED;
	}
	gf_service_connect_ack(serv, NULL, reply);
	if (!reply && read->is_inline ) AC3_SetupObject(read);
	return GF_OK;
}
Esempio n. 4
0
File: img_in.c Progetto: Bevara/GPAC
static GF_Err IMG_ConnectService(GF_InputService *plug, GF_ClientService *serv, const char *url)
{
    char *sExt;
    IMGLoader *read = (IMGLoader *)plug->priv;

    read->service = serv;
    if (!url)
        return GF_BAD_PARAM;
    sExt = strrchr(url, '.');
    if (!stricmp(sExt, ".jpeg") || !stricmp(sExt, ".jpg")) read->img_type = IMG_JPEG;
    else if (!stricmp(sExt, ".png")) read->img_type = IMG_PNG;
    else if (!stricmp(sExt, ".pngd")) read->img_type = IMG_PNGD;
    else if (!stricmp(sExt, ".pngds")) read->img_type = IMG_PNGDS;
    else if (!stricmp(sExt, ".pngs")) read->img_type = IMG_PNGS;
    else if (!stricmp(sExt, ".bmp")) read->img_type = IMG_BMP;

    if (read->dnload) gf_service_download_del(read->dnload);
    read->dnload = NULL;

    /*remote fetch*/
    if (!jp_is_local(url)) {
        jp_download_file(plug, url);
        return GF_OK;
    }

    read->stream = fopen(url, "rb");
    if (read->stream) {
        gf_f64_seek(read->stream, 0, SEEK_END);
        read->data_size = (u32) gf_f64_tell(read->stream);
        gf_f64_seek(read->stream, 0, SEEK_SET);
    }
    gf_service_connect_ack(serv, NULL, read->stream ? GF_OK : GF_URL_ERROR);
    if (read->stream && read->is_inline) IMG_SetupObject(read);
    return GF_OK;
}
Esempio n. 5
0
void RP_ConfirmChannelConnect(RTPStream *ch, GF_Err e)
{
	GF_NetworkCommand com;

	/*in case the channel has been disconnected while SETUP was issued&processed. We also could
	clean up the command stack*/
	if (!ch->channel) return;

	gf_service_connect_ack(ch->owner->service, ch->channel, e);
	if (e != GF_OK || !ch->rtp_ch) return;

	/*success, overwrite SL config*/
	memset(&com, 0, sizeof(GF_NetworkCommand));
	com.command_type =	GF_NET_CHAN_RECONFIG;
	com.base.on_channel = ch->channel;

	gf_rtp_depacketizer_get_slconfig(ch->depacketizer, &com.cfg.sl_config);
	/*reconfig*/
	gf_service_command(ch->owner->service, &com, GF_OK);

	/*ISMACryp config*/
	if (ch->depacketizer->flags & GF_RTP_HAS_ISMACRYP) {
		memset(&com, 0, sizeof(GF_NetworkCommand));
		com.base.on_channel = ch->channel;
		com.command_type = GF_NET_CHAN_DRM_CFG;
		com.drm_cfg.scheme_type = ch->depacketizer->isma_scheme;
		com.drm_cfg.scheme_version = 1;
		/*not transported in SDP!!!*/
		com.drm_cfg.scheme_uri = NULL;
		com.drm_cfg.kms_uri = ch->depacketizer->key;
		gf_service_command(ch->owner->service, &com, GF_OK);
	}
}
Esempio n. 6
0
void IMG_NetIO(void *cbk, GF_NETIO_Parameter *param)
{
	GF_Err e;
	const char *szCache;
	IMGLoader *read = (IMGLoader *) cbk;
	if (!read->dnload) return;

	/*handle service message*/
	gf_service_download_update_stats(read->dnload);

	e = param->error;
	/*wait to get the whole file*/
	if (!e && (param->msg_type!=GF_NETIO_DATA_TRANSFERED)) return;
	if ((e==GF_EOS) && (param->msg_type==GF_NETIO_DATA_EXCHANGE)) return;

	if (param->msg_type==GF_NETIO_DATA_TRANSFERED) {
		szCache = gf_dm_sess_get_cache_name(read->dnload);
		if (!szCache) e = GF_IO_ERR;
		else {
			if (read->stream) gf_fclose(read->stream);
			read->stream = gf_fopen((char *) szCache, "rb");
			if (!read->stream) e = GF_SERVICE_ERROR;
			else {
				e = GF_OK;
				gf_fseek(read->stream, 0, SEEK_END);
				read->data_size = (u32) gf_ftell(read->stream);
				gf_fseek(read->stream, 0, SEEK_SET);
			}
		}
	}
	/*OK confirm*/
	gf_service_connect_ack(read->service, NULL, e);
	if (!e) IMG_SetupObject(read);
}
Esempio n. 7
0
void VTT_NetIO(void *cbk, GF_NETIO_Parameter *param)
{
	GF_Err e;
	const char *szCache;
	GF_InputService *plug = (GF_InputService *)cbk;
	VTTIn *vttin = (VTTIn *) plug->priv;

	if (!vttin)	return;
	gf_service_download_update_stats(vttin->dnload);

	e = param->error;
	/*done*/
	if (param->msg_type==GF_NETIO_DATA_TRANSFERED) {
		szCache = gf_dm_sess_get_cache_name(vttin->dnload);
		if (!szCache) e = GF_IO_ERR;
		else {
			//e = TTIn_LoadFile(plug, szCache, 1);
		}
	}
	else if (param->msg_type==GF_NETIO_DATA_EXCHANGE) {
		return;
	}

	/*OK confirm*/
	if (vttin->needs_connection) {
		vttin->needs_connection = GF_FALSE;
		gf_service_connect_ack(vttin->service, NULL, e);
		//if (!e && !vttin->od_done) tti_setup_object(vttin);
	}
}
Esempio n. 8
0
static GF_Err IMG_ConnectChannel(GF_InputService *plug, LPNETCHANNEL channel, const char *url, Bool upstream)
{
	u32 ES_ID=0;
	GF_Err e;
	IMGLoader *read;
	if (!plug)
		return GF_OK;
	read = (IMGLoader *)plug->priv;

	e = GF_SERVICE_ERROR;
	if (read->ch==channel) goto exit;
	if (!url)
		goto exit;
	e = GF_STREAM_NOT_FOUND;
	if (strstr(url, "ES_ID")) {
		sscanf(url, "ES_ID=%ud", &ES_ID);
	}
	/*URL setup*/
	else if (!read->ch && IMG_CanHandleURL(plug, url)) ES_ID = 1;

	if (ES_ID==1) {
		read->ch = channel;
		e = GF_OK;
	}

exit:
	gf_service_connect_ack(read->service, channel, e);
	return e;
}
Esempio n. 9
0
static void AC3_OnLiveData(AC3Reader *read, const char *data, u32 data_size)
{
	u64 pos;
	Bool sync;
	GF_BitStream *bs;
	GF_AC3Header hdr;

	memset(&hdr, 0, sizeof(GF_AC3Header));

	read->data = gf_realloc(read->data, sizeof(char)*(read->data_size+data_size) );
	memcpy(read->data + read->data_size, data, sizeof(char)*data_size);
	read->data_size += data_size;

	if (read->needs_connection) {
		read->needs_connection = 0;
		bs = gf_bs_new((char *) read->data, read->data_size, GF_BITSTREAM_READ);
		sync = gf_ac3_parser_bs(bs, &hdr, GF_TRUE);
		gf_bs_del(bs);
		if (!sync) return;
		read->nb_ch = hdr.channels;
		read->sample_rate = hdr.sample_rate;
		read->is_live = 1;
		memset(&read->sl_hdr, 0, sizeof(GF_SLHeader));
		gf_service_connect_ack(read->service, NULL, GF_OK);
		AC3_SetupObject(read);
	}
	if (!read->ch) return;

	/*need a full ac3 header*/
	if (read->data_size<=7) return;

	bs = gf_bs_new((char *) read->data, read->data_size, GF_BITSTREAM_READ);
	hdr.framesize = 0;
	pos = 0;
	while (gf_ac3_parser_bs(bs, &hdr, GF_FALSE)) {
		pos = gf_bs_get_position(bs);
		read->sl_hdr.accessUnitStartFlag = 1;
		read->sl_hdr.accessUnitEndFlag = 1;
		read->sl_hdr.AU_sequenceNumber++;
		read->sl_hdr.compositionTimeStampFlag = 1;
		read->sl_hdr.compositionTimeStamp += 1536;
		gf_service_send_packet(read->service, read->ch, (char *) read->data + pos, hdr.framesize, &read->sl_hdr, GF_OK);
		gf_bs_skip_bytes(bs, hdr.framesize);
	}

	pos = gf_bs_get_position(bs);
	gf_bs_del(bs);

	if (pos) {
		u8 *d;
		read->data_size -= (u32) pos;
		d = gf_malloc(sizeof(char) * read->data_size);
		memcpy(d, read->data + pos, sizeof(char) * read->data_size);
		gf_free(read->data);
		read->data = d;
	}
	AC3_RegulateDataRate(read);
}
Esempio n. 10
0
GF_Err DC_ConnectChannel(GF_InputService *plug, LPNETCHANNEL channel, const char *url, Bool upstream)
{
	u32 ESID;
	DCReader *read = (DCReader *) plug->priv;

	sscanf(url, "ES_ID=%ud", &ESID);
	if (!ESID) {
		gf_service_connect_ack(read->service, channel, GF_STREAM_NOT_FOUND);
	} else {
		DummyChannel *dc;
		GF_SAFEALLOC(dc, DummyChannel);
		dc->ch = channel;
		dc->ESID = ESID;
		gf_list_add(read->channels, dc);
		gf_service_connect_ack(read->service, channel, GF_OK);
	}
	return GF_OK;
}
Esempio n. 11
0
void DC_DownloadFile(GF_InputService *plug, char *url)
{
	DCReader *read = (DCReader *) plug->priv;

	read->dnload = gf_service_download_new(read->service, url, 0, DC_NetIO, read);
	if (!read->dnload) {
		gf_service_connect_ack(read->service, NULL, GF_NOT_SUPPORTED);
	} else {
		/*start our download (threaded)*/
		gf_dm_sess_process(read->dnload);
	}
}
Esempio n. 12
0
u32 RP_Thread(void *param)
{
    u32 i;
    GF_NetworkCommand com;
    RTSPSession *sess;
    RTPStream *ch;
    RTPClient *rtp = (RTPClient *)param;

    rtp->th_state = 1;
    com.command_type = GF_NET_CHAN_BUFFER_QUERY;
    while (rtp->th_state) {
        gf_mx_p(rtp->mx);

        /*fecth data on udp*/
        i=0;
        while ((ch = (RTPStream *)gf_list_enum(rtp->channels, &i))) {
            if ((ch->flags & RTP_EOS) || (ch->status!=RTP_Running) ) continue;
            /*for interleaved channels don't read too fast, query the buffer occupancy*/
            if (ch->flags & RTP_INTERLEAVED) {
                com.base.on_channel = ch->channel;
                gf_service_command(rtp->service, &com, GF_OK);
                /*if no buffering, use a default value (3 sec of data should do it)*/
                if (!com.buffer.max) com.buffer.max = 3000;
                if (com.buffer.occupancy <= com.buffer.max) ch->rtsp->flags |= RTSP_TCP_FLUSH;
            } else {
                RP_ReadStream(ch);
            }
        }

        /*and process commands / flush TCP*/
        i=0;
        while ((sess = (RTSPSession *)gf_list_enum(rtp->sessions, &i))) {
            RP_ProcessCommands(sess);

            if (sess->connect_error) {
                gf_service_connect_ack(sess->owner->service, NULL, sess->connect_error);
                sess->connect_error = 0;
            }

        }

        gf_mx_v(rtp->mx);

        gf_sleep(1);
    }

    if (rtp->dnload) gf_service_download_del(rtp->dnload);
    rtp->dnload = NULL;

    rtp->th_state = 2;
    return 0;
}
Esempio n. 13
0
void jp_download_file(GF_InputService *plug, const char *url)
{
	IMGLoader *read = (IMGLoader *) plug->priv;

	read->dnload = gf_service_download_new(read->service, url, 0, IMG_NetIO, read);
	if (!read->dnload) {
		gf_service_connect_ack(read->service, NULL, GF_NOT_SUPPORTED);
	} else {
		/*start our download (threaded)*/
		gf_dm_sess_process(read->dnload);
	}
	/*service confirm is done once fetched*/
}
Esempio n. 14
0
File: saf_in.c Progetto: Bevara/GPAC
static void SAF_DownloadFile(GF_InputService *plug, char *url)
{
	SAFIn *read = (SAFIn*) plug->priv;

	read->dnload = gf_service_download_new(read->service, url, 0, SAF_NetIO, read);
	if (!read->dnload) {
		read->needs_connection = 0;
		gf_service_connect_ack(read->service, NULL, GF_NOT_SUPPORTED);
	} else {
		/*start our download (threaded)*/
		gf_dm_sess_process(read->dnload);
	}
	/*service confirm is done once fetched*/
}
Esempio n. 15
0
void isor_setup_download(GF_InputService *plug, const char *url)
{
	ISOMReader *read = (ISOMReader *) plug->priv;
	read->dnload = gf_service_download_new(read->service, url, 0, isor_net_io, read);
	if (!read->dnload) {
		if (read->input->query_proxy && read->input->proxy_udta && read->input->proxy_type) {
			send_proxy_command(read, GF_FALSE, GF_FALSE, GF_NOT_SUPPORTED, NULL, NULL);
		} else {
			gf_service_connect_ack(read->service, NULL, GF_NOT_SUPPORTED);
		}
	} else {
		/*start our download (threaded)*/
		gf_dm_sess_process(read->dnload);
	}
	/*service confirm is done once IOD can be fetched*/
}
Esempio n. 16
0
void VTT_download_file(GF_InputService *plug, const char *url)
{
	VTTIn *vttin = (VTTIn *) plug->priv;
	if (!plug || !url)
		return;
	vttin->needs_connection = GF_TRUE;
	vttin->dnload = gf_service_download_new(vttin->service, url, 0, VTT_NetIO, plug);
	if (!vttin->dnload) {
		vttin->needs_connection = GF_FALSE;
		gf_service_connect_ack(vttin->service, NULL, GF_NOT_SUPPORTED);
	} else {
		/*start our download (threaded)*/
		gf_dm_sess_process(vttin->dnload);
	}
	/*service confirm is done once fetched*/
}
Esempio n. 17
0
void ac3_download_file(GF_InputService *plug, char *url)
{
	AC3Reader *read = (AC3Reader*) plug->priv;

	read->needs_connection = GF_TRUE;

	read->dnload = gf_service_download_new(read->service, url, 0, AC3_NetIO, read);
	if (!read->dnload ) {
		read->needs_connection = GF_FALSE;
		gf_service_connect_ack(read->service, NULL, GF_NOT_SUPPORTED);
	} else {
		/*start our download (threaded)*/
		gf_dm_sess_process(read->dnload);
	}
	/*service confirm is done once fetched*/
}
Esempio n. 18
0
void RP_SDPFromData(RTPClient *rtp, char *s_url, RTPStream *stream)
{
	char *url;
	char buf[2000];
	u32 size;

	url = strstr(s_url, ",");
	if (!url) {
		gf_service_connect_ack(rtp->service, NULL, GF_URL_ERROR);
		return;
	}
	url += 1;
	if (strstr(url, ";base64")) {
		//decode
		size = gf_base64_decode(url, (u32) strlen(url), buf, 2000);
		buf[size] = 0;
		url = buf;
	}
	RP_LoadSDP(rtp, url, (u32) strlen(url), stream);
}
Esempio n. 19
0
static GF_Err VTT_ConnectChannel(GF_InputService *plug, LPNETCHANNEL channel, const char *url, Bool upstream)
{
	u32 ES_ID;
	GF_Err e;
	VTTIn *vttin = (VTTIn *)plug->priv;
	if (!vttin)	return GF_BAD_PARAM;
	e = GF_SERVICE_ERROR;
	if (!vttin || vttin->channel==channel) goto exit;

	e = GF_STREAM_NOT_FOUND;
	ES_ID = 0;
	if (strstr(url, "ES_ID")) sscanf(url, "ES_ID=%ud", &ES_ID);

	if (ES_ID==1) {
		vttin->channel = channel;
		e = GF_OK;
	}

exit:
	gf_service_connect_ack(vttin->service, channel, e);
	return e;
}
Esempio n. 20
0
static GF_Err FFD_ConnectChannel(GF_InputService *plug, LPNETCHANNEL channel, const char *url, Bool upstream)
{
	GF_Err e;
	u32 ESID;
	FFDemux *ffd = plug->priv;

	e = GF_STREAM_NOT_FOUND;
	if (upstream) {
		e = GF_ISOM_INVALID_FILE;
		goto exit;
	}
	if (!strstr(url, "ES_ID=")) {
		e = GF_NOT_SUPPORTED;
		goto exit;
	}
	sscanf(url, "ES_ID=%u", &ESID);

	if ((s32) ESID == 1 + ffd->audio_st) {
		if (ffd->audio_ch) {
			e = GF_SERVICE_ERROR;
			goto exit;
		}
		ffd->audio_ch = channel;
		e = GF_OK;
	}
	else if ((s32) ESID == 1 + ffd->video_st) {
		if (ffd->video_ch) {
			e = GF_SERVICE_ERROR;
			goto exit;
		}
		ffd->video_ch = channel;
		e = GF_OK;
	}

exit:
	gf_service_connect_ack(ffd->service, channel, e);
	return GF_OK;
}
Esempio n. 21
0
void DC_NetIO(void *cbk, GF_NETIO_Parameter *param)
{
	GF_Err e;
	DCReader *read = (DCReader *) cbk;

	/*handle service message*/
	gf_service_download_update_stats(read->dnload);

	e = param->error;

	if (param->msg_type==GF_NETIO_DATA_TRANSFERED) {
	} else if (param->msg_type==GF_NETIO_PARSE_HEADER) {
		if (!strcmp(param->name, "Content-Type")) {
			if (strstr(param->value, "application/x-bt")) read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;
			if (strstr(param->value, "application/x-xmt")) read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;
			if (strstr(param->value, "model/vrml")) read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;
			if (strstr(param->value, "model/x3d+vrml")) read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;
			if (strstr(param->value, "application/x-shockwave-flash")) read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;
			if (strstr(param->value, "image/svg+xml")) read->oti = GPAC_OTI_PRIVATE_SCENE_SVG;
			if (strstr(param->value, "image/x-svgm")) read->oti = GPAC_OTI_PRIVATE_SCENE_SVG;
			if (strstr(param->value, "application/x-LASeR+xml")) read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;
			if (strstr(param->value, "application/widget")) read->oti = GPAC_OTI_PRIVATE_SCENE_WGT;
			if (strstr(param->value, "application/x-mpegu-widget")) read->oti = GPAC_OTI_PRIVATE_SCENE_WGT;
		}
		return;
	} else if (!e && (param->msg_type!=GF_NETIO_DATA_EXCHANGE)) return;

	if (!e && !read->oti)
		return;

	/*OK confirm*/
	if (!read->is_service_connected) {
		if (!gf_dm_sess_get_cache_name(read->dnload)) e = GF_IO_ERR;
		if (e>0) e = GF_OK;
		gf_service_connect_ack(read->service, NULL, e);
		read->is_service_connected = GF_TRUE;
	}
}
Esempio n. 22
0
static GF_Err VTT_ConnectService(GF_InputService *plug, GF_ClientService *serv, const char *url)
{
	GF_Err e;
	VTTIn *vttin = (VTTIn *)plug->priv;
	if (!plug || !url)
		return GF_BAD_PARAM;
	vttin->service = serv;

	if (vttin->dnload) gf_service_download_del(vttin->dnload);
	vttin->dnload = NULL;

	/*remote fetch*/
	if (!VTT_is_local(url)) {
		VTT_download_file(plug, url);
		return GF_OK;
	} else {
		e = GF_OK;
		//e = TTIn_LoadFile(plug, url, 0);
		gf_service_connect_ack(serv, NULL, e);
		//if (!e && !vttin->od_done) tti_setup_object(vttin);
	}
	return GF_OK;
}
Esempio n. 23
0
void RP_FetchSDP(RTPClient *rtp, char *url, RTPStream *stream, char *original_url)
{
	SDPFetch *sdp;
	/*if local URL get file*/
	if (strstr(url, "data:application/sdp")) {
		RP_SDPFromData(rtp, url, stream);
		return;
	}
	if (!strnicmp(url, "file://", 7) || !strstr(url, "://")) {
		RP_SDPFromFile(rtp, url, stream);
		return;
	}

	sdp = (SDPFetch*)gf_malloc(sizeof(SDPFetch));
	memset(sdp, 0, sizeof(SDPFetch));
	sdp->client = rtp;
	sdp->remote_url = gf_strdup(url);
	sdp->chan = stream;
	if (original_url) {
		sdp->original_url = gf_strdup(original_url);
	}

	/*otherwise setup download*/
	if (rtp->dnload) gf_service_download_del(rtp->dnload);
	rtp->dnload = NULL;

	rtp->sdp_temp = sdp;
	rtp->dnload = gf_service_download_new(rtp->service, url, 0, SDP_NetIO, rtp);
	if (!rtp->dnload) {
		gf_service_connect_ack(rtp->service, NULL, GF_NOT_SUPPORTED);
	} else {
		/*start our download (threaded)*/
		gf_dm_sess_process(rtp->dnload);
	}
	/*service confirm is done once fetched*/
}
Esempio n. 24
0
File: saf_in.c Progetto: Bevara/GPAC
static GF_Err SAF_ConnectService(GF_InputService *plug, GF_ClientService *serv, const char *url)
{
	char szURL[2048];
	char *ext;
	SAFIn *read = (SAFIn *)plug->priv;
	read->service = serv;

	if (read->dnload) gf_service_download_del(read->dnload);
	read->dnload = NULL;

	strcpy(szURL, url);
	ext = strrchr(szURL, '#');
	if (ext) ext[0] = 0;

	read->needs_connection = 1;
	read->duration = 0;

	read->saf_type = SAF_FILE_LOCAL;
	/*remote fetch*/
	if (strnicmp(url, "file://", 7) && strstr(url, "://")) {
		read->saf_type = SAF_FILE_REMOTE;
		SAF_DownloadFile(plug, (char *) szURL);
		return GF_OK;
	}

	read->stream = gf_f64_open(szURL, "rb");
	if (!read->stream) {
		gf_service_connect_ack(serv, NULL, GF_URL_ERROR);
		return GF_OK;
	}
	SAF_CheckFile(read);
	read->th = gf_th_new("SAFDemux");
	/*start playing for tune-in*/
	gf_th_run(read->th, SAF_Run, read);
	return GF_OK;
}
Esempio n. 25
0
File: saf_in.c Progetto: Bevara/GPAC
static GF_Err SAF_ConnectChannel(GF_InputService *plug, LPNETCHANNEL channel, const char *url, Bool upstream)
{
	u32 ES_ID;
	SAFChannel *ch;
	GF_Err e;
	SAFIn *read = (SAFIn *)plug->priv;


	ch = saf_get_channel(read, 0, channel);
	if (ch) e = GF_SERVICE_ERROR;

	e = GF_STREAM_NOT_FOUND;
	if (strstr(url, "ES_ID")) {
		sscanf(url, "ES_ID=%d", &ES_ID);
		ch = saf_get_channel(read, ES_ID, NULL);
		if (ch && !ch->ch) {
			ch->ch = channel;
			e = GF_OK;
		}
	}

	gf_service_connect_ack(read->service, channel, e);
	return e;
}
Esempio n. 26
0
/* Callback functions used by a media parser when parsing events happens */
GF_Err gf_mse_proxy(GF_InputService *parser, GF_NetworkCommand *command)
{
	if (!parser || !command || !parser->proxy_udta) {
		return GF_BAD_PARAM;
	} else {
		GF_HTML_SourceBuffer *sb = (GF_HTML_SourceBuffer *)parser->proxy_udta;
		switch (command->command_type) {
		case GF_NET_SERVICE_QUERY_INIT_RANGE:
			break;
		case GF_NET_SERVICE_QUERY_NEXT:
			/* The parser is asking for the next media segment in the buffer,
			   check for the media time and give the right one */
		{
			GF_HTML_ArrayBuffer *buffer;
			/* The input buffer should not be modified by append operations at the same time, no need to protect access */
			buffer = (GF_HTML_ArrayBuffer *)gf_list_get(sb->input_buffer, 0);
			if (buffer) {
				command->url_query.discontinuity_type = 0;
				command->url_query.current_download = GF_FALSE;
				command->url_query.start_range = 0;
				command->url_query.end_range = 0;
				command->url_query.switch_start_range = 0;
				command->url_query.switch_end_range = 0;
				command->url_query.next_url_init_or_switch_segment = NULL;
				if (buffer->is_init) {
					GF_HTML_ArrayBuffer *next = (GF_HTML_ArrayBuffer *)gf_list_get(sb->input_buffer, 1);
					command->url_query.discontinuity_type = 1;
					if (next) {
						GF_LOG(GF_LOG_DEBUG, GF_LOG_DASH, ("[MSE] Next segment to parse %s with init \n", next->url, buffer->url));
						command->url_query.next_url = next->url;
						command->url_query.next_url_init_or_switch_segment = buffer->url;
						gf_list_rem(sb->input_buffer, 0);
						gf_list_rem(sb->input_buffer, 0);
					} else {
						GF_LOG(GF_LOG_DEBUG, GF_LOG_DASH, ("[MSE] Only one init segment to parse %s, need to wait\n", buffer->url));
						command->url_query.next_url = NULL;
					}
				} else {
					GF_LOG(GF_LOG_DEBUG, GF_LOG_DASH, ("[MSE] Next segment to parse %s\n", buffer->url));
					command->url_query.next_url = buffer->url;
					gf_list_rem(sb->input_buffer, 0);
				}
				sb->prev_buffer = buffer;
			} else {
				command->url_query.next_url = NULL;
				command->url_query.discontinuity_type = 0;
			}
		}
		break;
		case GF_NET_SERVICE_STATUS_PROXY:
			/* The parser is informing the proxy about its status changes:
			    - new track found
				- all tracks parsed
				- connect/disconnect
				- */
			if (command->status.is_add_media) {
				if (command->status.desc) {
					gf_mse_source_buffer_store_track_desc(sb, (GF_ObjectDescriptor *)command->status.desc);
				} else {
					/* this is the last add media, we can switch updating to false */
					/* the first init segment was correctly processed */
					gf_mse_source_buffer_set_update(sb, GF_FALSE);
					/* TODO: set active tracks and send addsourcebuffer event */
					/* TODO: send media loadedmetadata event */
				}
				gf_service_declare_media(sb->mediasource->service, command->status.desc, (command->status.desc ? GF_TRUE : GF_FALSE));
			}
			/* general connection/disconnection messages from the media parser (not track related) */
			else if (!command->status.channel) {
				/* connection message */
				if (!command->status.is_disconnect) {
					if (command->status.e == GF_OK) {
						/* nothing needs to be done. Setup is done with final add media */
						sb->parser_connected = GF_TRUE;
						sb->mediasource->durationType = DURATION_INFINITY;
						gf_mse_source_buffer_setup_tracks(sb);
					} else {
						/* wrong first init segment */
						/* TODO: fire an error event */
					}
					gf_service_connect_ack(sb->mediasource->service, command->status.channel, command->status.e);
				} else {
					gf_service_disconnect_ack(sb->mediasource->service, command->status.channel, command->status.e);
				}
			}
			/* channel (track related) specific connection/disconnection messages from the media parser */
			else {
				if (!command->status.is_disconnect) {
					gf_service_connect_ack(sb->mediasource->service, command->status.channel, command->status.e);
				} else {
					gf_service_disconnect_ack(sb->mediasource->service, command->status.channel, command->status.e);
				}
			}
			break;
		default:
			gf_service_command(sb->mediasource->service, command, GF_OK);
			break;
		}
		return GF_OK;
	}
}
Esempio n. 27
0
GF_Err DC_ConnectService(GF_InputService *plug, GF_ClientService *serv, const char *url)
{
	DCReader *read = (DCReader *) plug->priv;
	FILE *test;
	char *tmp, *ext;

	if (!read || !serv || !url) return GF_BAD_PARAM;

	if (read->dnload) gf_service_download_del(read->dnload);
	read->dnload = NULL;

	read->url = gf_strdup(url);
	ext = strchr(read->url, '#');
	if (ext) {
		char *anext;
		ext[0] = 0;
		anext = strrchr(read->url, '.');
		ext[0] = '#';
		ext = anext;
	} else {
		ext = strrchr(read->url, '.');
	}
	if (ext && !stricmp(ext, ".gz")) {
		char *anext;
		ext[0] = 0;
		anext = strrchr(read->url, '.');
		ext[0] = '.';
		ext = anext;
	}
	read->service = serv;

	if (!strnicmp(url, "views://", 8)) {
		read->is_views_url = GF_TRUE;
		gf_service_connect_ack(serv, NULL, GF_OK);
		read->is_service_connected = GF_TRUE;
		return GF_OK;
	}

	if (ext) {
		char *cgi_par = NULL;
		ext += 1;
		if (ext) {
			tmp = strchr(ext, '#');
			if (tmp) tmp[0] = 0;
			/* Warning the '?' sign should not be present in local files but it is convenient to have it
			   to test web content locally */
			cgi_par = strchr(ext, '?');
			if (cgi_par) cgi_par[0] = 0;
		}
		if (!stricmp(ext, "bt") || !stricmp(ext, "btz") || !stricmp(ext, "bt.gz")
		        || !stricmp(ext, "xmta")
		        || !stricmp(ext, "xmt") || !stricmp(ext, "xmt.gz") || !stricmp(ext, "xmtz")
		        || !stricmp(ext, "wrl") || !stricmp(ext, "wrl.gz")
		        || !stricmp(ext, "x3d") || !stricmp(ext, "x3d.gz") || !stricmp(ext, "x3dz")
		        || !stricmp(ext, "x3dv") || !stricmp(ext, "x3dv.gz") || !stricmp(ext, "x3dvz")
		        || !stricmp(ext, "swf")
		   )
			read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;

		else if (!stricmp(ext, "svg") || !stricmp(ext, "svgz") || !stricmp(ext, "svg.gz")) {
			read->oti = GPAC_OTI_PRIVATE_SCENE_SVG;
		}
		/*XML LASeR*/
		else if (!stricmp(ext, "xsr"))
			read->oti = GPAC_OTI_PRIVATE_SCENE_LASER;
		else if (!stricmp(ext, "xbl"))
			read->oti = GPAC_OTI_PRIVATE_SCENE_XBL;
		else if (!stricmp(ext, "wgt") || !stricmp(ext, "mgt"))
			read->oti = GPAC_OTI_PRIVATE_SCENE_WGT;

		if (cgi_par) cgi_par[0] = '?';
	}

	if (!read->oti && (!strnicmp(url, "file://", 7) || !strstr(url, "://"))) {
		char *rtype = gf_xml_get_root_type(url, NULL);
		if (rtype) {
			if (!strcmp(rtype, "SAFSession")) read->oti = GPAC_OTI_PRIVATE_SCENE_LASER;
			else if (!strcmp(rtype, "svg")) read->oti = GPAC_OTI_PRIVATE_SCENE_SVG;
			else if (!strcmp(rtype, "XMT-A")) read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;
			else if (!strcmp(rtype, "X3D")) read->oti = GPAC_OTI_PRIVATE_SCENE_GENERIC;
			else if (!strcmp(rtype, "bindings")) read->oti = GPAC_OTI_PRIVATE_SCENE_XBL;
			else if (!strcmp(rtype, "widget")) read->oti = GPAC_OTI_PRIVATE_SCENE_WGT;
			gf_free(rtype);
		}
	}

	/*remote fetch*/
	if (!strnicmp(url, "file://", 7)) {
		url += 7;
	}
	else if (strstr(url, "://")) {
		DC_DownloadFile(plug, read->url);
		return GF_OK;
	}

	test = gf_fopen(read->url, "rt");
	if (!test) {
		gf_service_connect_ack(serv, NULL, GF_URL_ERROR);
		return GF_OK;
	}
	gf_fclose(test);
	if (!read->is_service_connected) {
		gf_service_connect_ack(serv, NULL, GF_OK);
		read->is_service_connected = GF_TRUE;
	}
	return GF_OK;
}
Esempio n. 28
0
static GF_Err FFD_ConnectService(GF_InputService *plug, GF_ClientService *serv, const char *url)
{
	GF_Err e;
	s64 last_aud_pts;
	u32 i;
	s32 res;
	Bool is_local;
	const char *sOpt;
	char *ext, szName[1024];
	FFDemux *ffd = plug->priv;
	AVInputFormat *av_in = NULL;
	char szExt[20];

	if (ffd->ctx) return GF_SERVICE_ERROR;

	assert( url && strlen(url) < 1024);
	strcpy(szName, url);
	ext = strrchr(szName, '#');
	ffd->service_type = 0;
	e = GF_NOT_SUPPORTED;
	ffd->service = serv;

	if (ext) {
		if (!stricmp(&ext[1], "video")) ffd->service_type = 1;
		else if (!stricmp(&ext[1], "audio")) ffd->service_type = 2;
		ext[0] = 0;
	}

	/*some extensions not supported by ffmpeg, overload input format*/
	ext = strrchr(szName, '.');
	strcpy(szExt, ext ? ext+1 : "");
	strlwr(szExt);
	if (!strcmp(szExt, "cmp")) av_in = av_find_input_format("m4v");

	is_local = (strnicmp(url, "file://", 7) && strstr(url, "://")) ? 0 : 1;

	GF_LOG(GF_LOG_DEBUG, GF_LOG_CONTAINER, ("[FFMPEG] opening file %s - local %d - av_in %08x\n", url, is_local, av_in));

	if (!is_local) {
		AVProbeData   pd;

		/*setup wraper for FFMPEG I/O*/
		ffd->buffer_size = 8192;
		sOpt = gf_modules_get_option((GF_BaseInterface *)plug, "FFMPEG", "IOBufferSize");
		if (sOpt) ffd->buffer_size = atoi(sOpt);
		ffd->buffer = gf_malloc(sizeof(char)*ffd->buffer_size);
#ifdef FFMPEG_DUMP_REMOTE
		ffd->outdbg = gf_f64_open("ffdeb.raw", "wb");
#endif
#ifdef USE_PRE_0_7
		init_put_byte(&ffd->io, ffd->buffer, ffd->buffer_size, 0, ffd, ff_url_read, NULL, NULL);
		ffd->io.is_streamed = 1;
#else
		ffd->io.seekable = 1;
#endif

		ffd->dnload = gf_service_download_new(ffd->service, url, GF_NETIO_SESSION_NOT_THREADED  | GF_NETIO_SESSION_NOT_CACHED, NULL, ffd);
		if (!ffd->dnload) return GF_URL_ERROR;
		while (1) {
			u32 read;
			e = gf_dm_sess_fetch_data(ffd->dnload, ffd->buffer + ffd->buffer_used, ffd->buffer_size - ffd->buffer_used, &read);
			if (e==GF_EOS) break;
			/*we're sync!!*/
			if (e==GF_IP_NETWORK_EMPTY) continue;
			if (e) goto err_exit;
			ffd->buffer_used += read;
			if (ffd->buffer_used == ffd->buffer_size) break;
		}
		if (e==GF_EOS) {
			const char *cache_file = gf_dm_sess_get_cache_name(ffd->dnload);
			res = open_file(&ffd->ctx, cache_file, av_in);
		} else {
			pd.filename = szName;
			pd.buf_size = ffd->buffer_used;
			pd.buf = (u8 *) ffd->buffer;
			av_in = av_probe_input_format(&pd, 1);
			if (!av_in) {
				GF_LOG(GF_LOG_ERROR, GF_LOG_CONTAINER, ("[FFMPEG] error probing file %s - probe start with %c %c %c %c\n", url, ffd->buffer[0], ffd->buffer[1], ffd->buffer[2], ffd->buffer[3]));
				return GF_NOT_SUPPORTED;
			}
			/*setup downloader*/
			av_in->flags |= AVFMT_NOFILE;
#ifdef USE_AVFORMAT_OPEN_INPUT /*commit ffmpeg 603b8bc2a109978c8499b06d2556f1433306eca7*/
			res = avformat_open_input(&ffd->ctx, szName, av_in, NULL);
#else
			res = av_open_input_stream(&ffd->ctx, &ffd->io, szName, av_in, NULL);
#endif
		}
	} else {
		res = open_file(&ffd->ctx, szName, av_in);
	}

	switch (res) {
#ifndef _WIN32_WCE
	case 0:
		e = GF_OK;
		break;
	case AVERROR_IO:
		e = GF_URL_ERROR;
		goto err_exit;
	case AVERROR_INVALIDDATA:
		e = GF_NON_COMPLIANT_BITSTREAM;
		goto err_exit;
	case AVERROR_NOMEM:
		e = GF_OUT_OF_MEM;
		goto err_exit;
	case AVERROR_NOFMT:
		e = GF_NOT_SUPPORTED;
		goto err_exit;
#endif
	default:
		e = GF_SERVICE_ERROR;
		goto err_exit;
	}

	GF_LOG(GF_LOG_DEBUG, GF_LOG_CONTAINER, ("[FFMPEG] looking for streams in %s - %d streams - type %s\n", ffd->ctx->filename, ffd->ctx->nb_streams, ffd->ctx->iformat->name));

	res = av_find_stream_info(ffd->ctx);
	if (res <0) {
		GF_LOG(GF_LOG_ERROR, GF_LOG_CONTAINER, ("[FFMPEG] cannot locate streams - error %d\n", res));
		e = GF_NOT_SUPPORTED;
		goto err_exit;
	}
	GF_LOG(GF_LOG_DEBUG, GF_LOG_CONTAINER, ("[FFMPEG] file %s opened - %d streams\n", url, ffd->ctx->nb_streams));

	/*figure out if we can use codecs or not*/
	ffd->audio_st = ffd->video_st = -1;
	for (i = 0; i < ffd->ctx->nb_streams; i++) {
		AVCodecContext *enc = ffd->ctx->streams[i]->codec;
		switch(enc->codec_type) {
		case AVMEDIA_TYPE_AUDIO:
			if ((ffd->audio_st<0) && (ffd->service_type!=1)) {
				ffd->audio_st = i;
				ffd->audio_tscale = ffd->ctx->streams[i]->time_base;
			}
			break;
		case AVMEDIA_TYPE_VIDEO:
			if ((ffd->video_st<0) && (ffd->service_type!=2)) {
				ffd->video_st = i;
				ffd->video_tscale = ffd->ctx->streams[i]->time_base;
			}
			break;
		default:
			break;
		}
	}
	if ((ffd->service_type==1) && (ffd->video_st<0)) goto err_exit;
	if ((ffd->service_type==2) && (ffd->audio_st<0)) goto err_exit;
	if ((ffd->video_st<0) && (ffd->audio_st<0)) {
		GF_LOG(GF_LOG_ERROR, GF_LOG_CONTAINER, ("[FFMPEG] No supported streams in file\n"));
		goto err_exit;
	}


	sOpt = gf_modules_get_option((GF_BaseInterface *)plug, "FFMPEG", "DataBufferMS");
	ffd->data_buffer_ms = 0;
	if (sOpt) ffd->data_buffer_ms = atoi(sOpt);
	if (!ffd->data_buffer_ms) ffd->data_buffer_ms = FFD_DATA_BUFFER;

	/*build seek*/
	if (is_local) {
		/*check we do have increasing pts. If not we can't rely on pts, we must skip SL
		we assume video pts is always present*/
		if (ffd->audio_st>=0) {
			last_aud_pts = 0;
			for (i=0; i<20; i++) {
				AVPacket pkt;
				pkt.stream_index = -1;
				if (av_read_frame(ffd->ctx, &pkt) <0) break;
				if (pkt.pts == AV_NOPTS_VALUE) pkt.pts = pkt.dts;
				if (pkt.stream_index==ffd->audio_st) last_aud_pts = pkt.pts;
			}
			if (last_aud_pts*ffd->audio_tscale.den<10*ffd->audio_tscale.num) ffd->unreliable_audio_timing = 1;
		}

		ffd->seekable = (av_seek_frame(ffd->ctx, -1, 0, AVSEEK_FLAG_BACKWARD)<0) ? 0 : 1;
		if (!ffd->seekable) {
#ifndef FF_API_CLOSE_INPUT_FILE
			av_close_input_file(ffd->ctx);
#else
			avformat_close_input(&ffd->ctx);
#endif
			ffd->ctx = NULL;
			open_file(&ffd->ctx, szName, av_in);
			av_find_stream_info(ffd->ctx);
		}
	}

	/*let's go*/
	gf_service_connect_ack(serv, NULL, GF_OK);
	/*if (!ffd->service_type)*/ FFD_SetupObjects(ffd);
	ffd->service_type = 0;
	return GF_OK;

err_exit:
	GF_LOG(GF_LOG_ERROR, GF_LOG_CONTAINER, ("[FFMPEG] Error opening file %s: %s\n", url, gf_error_to_string(e)));
#ifndef FF_API_CLOSE_INPUT_FILE
	if (ffd->ctx) av_close_input_file(ffd->ctx);
#else
	if (ffd->ctx) avformat_close_input(&ffd->ctx);
#endif
	ffd->ctx = NULL;
	gf_service_connect_ack(serv, NULL, e);
	return GF_OK;
}
Esempio n. 29
0
void SDP_NetIO(void *cbk, GF_NETIO_Parameter *param)
{
	GF_Err e;
	RTPClient *rtp = (RTPClient *)cbk;
	SDPFetch *sdp = rtp->sdp_temp;

	gf_service_download_update_stats(rtp->dnload);

	e = param->error;
	switch (param->msg_type) {
	case GF_NETIO_GET_METHOD:
		if (sdp->original_url)
			param->name = "POST";
		return;
	case GF_NETIO_GET_CONTENT:
		if (sdp->original_url) {
			char szBody[4096], *opt;
			opt = (char *) gf_modules_get_option((GF_BaseInterface *) gf_service_get_interface(rtp->service), "Network", "MobileIP");
			sprintf(szBody, "ipadd\n%s\n\nurl\n%s\n\n", opt, sdp->original_url);
			param->data = szBody;
			param->size = (u32) strlen(szBody);
		}
		return;
	case GF_NETIO_DATA_TRANSFERED:
		if (sdp->original_url) {
			u32 sdp_size;
			e = gf_dm_sess_get_stats(rtp->dnload, NULL, NULL, &sdp_size, NULL, NULL, NULL);
			if (sdp_size) {
				const char *szFile = gf_dm_sess_get_cache_name(rtp->dnload);
				if (!szFile) {
					e = GF_SERVICE_ERROR;
				} else {
					e = GF_OK;
					RP_SDPFromFile(rtp, (char *) szFile, sdp->chan);
					gf_free(sdp->remote_url);
					if (sdp->original_url) gf_free(sdp->original_url);
					gf_free(sdp);
					rtp->sdp_temp = NULL;
					return;
				}
			}
		}
		break;
	default:
		if (e == GF_OK) return;
	}

	if (sdp->original_url) {
		char *url = sdp->original_url;
		gf_free(sdp->remote_url);
		gf_free(sdp);
		rtp->sdp_temp = NULL;
		RP_SendMessage(rtp->service, e, "Error fetching session state - restarting");
		RP_ConnectServiceEx(gf_service_get_interface(rtp->service), rtp->service, url, GF_TRUE);
		gf_free(url);
		return;
	}

	/*error*/
	if (sdp->chan) {
		gf_service_connect_ack(rtp->service, sdp->chan->channel, e);
	} else {
		gf_service_connect_ack(rtp->service, NULL, e);
		rtp->sdp_temp = NULL;
	}
	gf_free(sdp->remote_url);
	if (sdp->original_url) gf_free(sdp->original_url);
	gf_free(sdp);
	rtp->sdp_temp = NULL;
}
Esempio n. 30
0
void AC3_NetIO(void *cbk, GF_NETIO_Parameter *param)
{
	GF_Err e;
	const char *szCache;
	u32 total_size, bytes_done;
	AC3Reader *read = (AC3Reader *) cbk;

	e = param->error;
	/*done*/
	if (param->msg_type==GF_NETIO_DATA_TRANSFERED) {
		if (read->stream) {
			read->is_remote = 0;
			e = GF_EOS;
		} else if (!read->needs_connection) {
			return;
		}
	} else if (param->msg_type==GF_NETIO_PARSE_HEADER) {
		if (!strcmp(param->name, "icy-name")) {
			if (read->icy_name) gf_free(read->icy_name);
			read->icy_name = gf_strdup(param->value);
		}
		if (!strcmp(param->name, "icy-genre")) {
			if (read->icy_genre) gf_free(read->icy_genre);
			read->icy_genre = gf_strdup(param->value);
		}
		if (!strcmp(param->name, "icy-meta")) {
			GF_NetworkCommand com;
			char *meta;
			if (read->icy_track_name) gf_free(read->icy_track_name);
			read->icy_track_name = NULL;
			meta = param->value;
			while (meta && meta[0]) {
				char *sep = strchr(meta, ';');
				if (sep) sep[0] = 0;

				if (!strnicmp(meta, "StreamTitle=", 12)) {
					read->icy_track_name = gf_strdup(meta+12);
				}
				if (!sep) break;
				sep[0] = ';';
				meta = sep+1;
			}

			com.base.command_type = GF_NET_SERVICE_INFO;
			gf_service_command(read->service, &com, GF_OK);
		}
		return;
	} else {
		/*handle service message*/
		gf_service_download_update_stats(read->dnload);
		if (param->msg_type!=GF_NETIO_DATA_EXCHANGE) return;
	}

	/*data fetching or EOS*/
	if (e >= GF_OK) {
		if (read->needs_connection) {
			gf_dm_sess_get_stats(read->dnload, NULL, NULL, &total_size, NULL, NULL, NULL);
			if (!total_size) read->is_live = 1;
		}
		if (read->is_live) {
			if (!e) AC3_OnLiveData(read, param->data, param->size);
			return;
		}
		if (read->stream) return;

		/*open service*/
		szCache = gf_dm_sess_get_cache_name(read->dnload);
		if (!szCache) e = GF_IO_ERR;
		else {
			read->stream = gf_f64_open((char *) szCache, "rb");
			if (!read->stream) e = GF_SERVICE_ERROR;
			else {
				/*if full file at once (in cache) parse duration*/
				if (e==GF_EOS) read->is_remote = 0;
				e = GF_OK;
				/*not enough data*/
				if (!AC3_ConfigureFromFile(read)) {
					/*get amount downloaded and check*/
					gf_dm_sess_get_stats(read->dnload, NULL, NULL, NULL, &bytes_done, NULL, NULL);
					if (bytes_done>10*1024) {
						e = GF_CORRUPTED_DATA;
					} else {
						fclose(read->stream);
						read->stream = NULL;
						return;
					}
				}
			}
		}
	}
	/*OK confirm*/
	if (read->needs_connection) {
		read->needs_connection = 0;
		gf_service_connect_ack(read->service, NULL, e);
		if (!e) AC3_SetupObject(read);
	}
}