We take a ref before removing which was never freeded.
The element is still alive anyway because the group has its own ref as
well.
Fix a leak with the 'test_suburi_error_wrongproto' test.
https://bugzilla.gnome.org/show_bug.cgi?id=766515
This helps in cases where raw audio data is being delivered, but the
buffers do not come in sample aligned sizes. The new unalignedaudioparse
bin can be autoplugged and configures an internal audioparse element to
align the data. audioparse itself gets support for audio/x-unaligned-raw
input caps; the output caps then contain the same information, except that
the name is changed to audio/x-raw (since audioparse aligns the data).
This ensures that souphttpsrc ! audioparse still works.
https://bugzilla.gnome.org/show_bug.cgi?id=689460
When we initialize an element in decodebin, we 1) set it to PAUSED and
push sticky events on its sinkpad to trigger negotiation 2) block its
src pad(s) to detect CAPS events. We can't block before 1) as that
would lead to a deadlock.
It's possible (and common) tho that an element configures its srcpad
during 1) and before 2). Therefore before this change we would
typically block and expose an element's pad only once the element
output its first buffer, triggering sticky events to be resent. One
consequence of this behaviour is that it sometimes broke
renegotiation.
With this change now we consider a pad ready to be exposed when it's
->blocked or has fixed caps (which were set before we could block it).
https://bugzilla.gnome.org/show_bug.cgi?id=765456
If we are configured to use buffering and there is no demuxer in the chain, we
still want a multiqueue, otherwise we will ignore the use-buffering property.
In that case, we will insert a multiqueue after the parser or decoder - not
elsewhere, otherwise we won't have timestamps.
https://bugzilla.gnome.org/show_bug.cgi?id=764948
gstsubparse.c: In function ‘parse_subrip’:
gstsubparse.c:988:7: error: ignoring return value of ‘strtol’, declared with attribute warn_unused_result [-Werror=unused-result]
cc1: all warnings being treated as errors
https://bugzilla.gnome.org/show_bug.cgi?id=765042
When blocking the subtitle pad, it's expected that stream-start
is the first event, and that it can precede caps arriving on the
peer pad - in fact the caps can only have arrived on the peer
pad when it was pre-primed with sticky events previously.
Instead, just pass the stream-start and don't block, because
stream-start is sticky anyway.
Don't require a cue identifier preceding the time range line
when parsing WebVTT. We could also store the CueID, but it's
not using anywhere, so just ignore it for now.
Make writable the buffer before pushing it lead to a buffer copy. It's
because a reference is keep for the previous buffer.
The previous buffer reference is only need to duplicate the buffer. In
drop-only mode, the previous buffer is release just after pushing the
buffer so a copy is done but it's useless.
https://bugzilla.gnome.org/show_bug.cgi?id=764319
Insert extra checks for the validity of the incoming
data when parsing subrip/webvtt content and debug log
output for invalid content.
Should fix Coverity warnings.
Remove some unused variables from the inner product functions.
Make filter coefficients by interpolating if required.
Rename some fields.
Try hard to not recalculate filters when just chaging the rate.
Add more proprties to audioresample.
Remove the consumed/produced output fields from the resampler and
converter. Let the caler specify the right number of input/output
samples so we can be more optimal.
Use just one function to update the converter configuration.
Simplify some things internally.
Make it possible to use writable input as temp space in audioconvert.
WebVTT is a new subtitle format for HTML5 video. In this first
version of the parser the cue settings are parsed but only stored in
the internal parser state structure. Later on these settings could be
part of the GstBuffer metadata.
https://bugzilla.gnome.org/show_bug.cgi?id=629764
There's a small window between decodebin choosing a buffering level
to post and another thread choosing a different buffering level
where things can race. Close that window by holding a new lock
that's only for posting buffering messages - like what was done
in multiqueue.
https://bugzilla.gnome.org/show_bug.cgi?id=764020
In check_upstream_seekable function, it returns FALSE value even though
we already declare about the seekable variable. So, This patch return
result of seekable in check_upstream_seekable function.
https://bugzilla.gnome.org/show_bug.cgi?id=763975
Due to transient locked state during autoplugging, some elements might be
ignored by the GstBin::change_state() and might still be running. Which could
then cause pad-added and similar accessing decodebin state that does not exist
anymore, and crash.
https://bugzilla.gnome.org/show_bug.cgi?id=763625
And also consider HEADER buffers without DELTA_UNIT flag as sync points. This
fixes sync-mode=2 with mpegtsmux for example, which has no streamheaders but
puts the HEADER flag on its keyframes.
https://bugzilla.gnome.org/show_bug.cgi?id=763278
In other places we lock it the other way around, leading to possible
deadlocks. Also this will deadlock if analyze_pad() causes a new element to be
autoplugged that adds new pads on itself when its state is changed.
https://bugzilla.gnome.org/show_bug.cgi?id=763491
This reverts commit 0615794300.
deinterlace was ported at some point in the last 4 years and has better video
format support, and especially better negotiation than avdeinterlace. Having
avdeinterlace but not deinterlace causes various problems in zerocopy
scenarios.
https://bugzilla.gnome.org/show_bug.cgi?id=760553
libgstreamer currently exports some debug category
symbols GST_CAT_*, but those are not declared in any
public headers.
Some plugins and libgstvideo just use GST_DEBUG_CATEGORY_EXTERN()
to declare and use those, but that's just not right at
all, and it won't work on Windows with MSVC. Instead look
up the categories via the API.
Avoids some false positives leading to miss identification:
* Prevent picture start code emulation for the first 2 bytes read
* Add check for valid "picture coding type" and "PB-frames mode" combination
Additionally, change name on confusingly named TR var to what
it is, the layer's PTYPE.
https://bugzilla.gnome.org/show_bug.cgi?id=693263
When getting caps of the decode chain, in get_topology, the caps are being
checked if fixed or not. But get_topology will be called when the decode is
chain is being exposed and hence it will always be fixed. Hence removing the
check for fixed caps. Removing gst_pad_get_current_caps for the chain->pad, as
get_pad_caps will again call the same api.
And get_topology can return NULL value if currently shutting down the
pipeline, which on being passed to create message will result in assertion
error. Check if topology is valid before using it
https://bugzilla.gnome.org/show_bug.cgi?id=755918
Avoid overflow in rate calculation. This can cause the resampler to
start on the wrong phase after a rate change.
Avoid overflow in cubic fraction calculation. This can cause noise when
dealing with higher samplerates.
analyze_new_pad() can return a new decode chain, which might have a new
GstDecodePad in the end. We should use those two for expose_pad() and not the
original ones that were passed to analyze_new_pad().
This fails when having a demuxer element that has raw pads immediately or
if a decoder with raw caps is after an adaptive demuxer.
https://bugzilla.gnome.org/show_bug.cgi?id=760949
[..] when resetting group start time. In GES, we are usually connected
to the streamsynchronizer on one audio and one video pad.
When seeking the timeline, both nlecompositions often output their flush_start
before any of them has output its flush_stop.
The current code, when receiving the first flush stop was using the
running time of the start of the second composition, which could
be pretty much anything, and means nothing at that point.
This patch is thread-safe, as STREAM_SYNCHRONIZER_LOCK is taken
both when setting flushing and when checking it.
https://bugzilla.gnome.org/show_bug.cgi?id=750013
When blocking input pads, we also need to properly set the appropriate
pending flag.
Without this, when switching stream types after initial configuration
(like going from Audio+Video to Audio+Video+Sub) playsink would never
wait for *all* input streams to be blocked (it would just wait for the
new input pad (text in this case) to be blocked).
Since the reconfiguration might introduce unlinking/relinking of elements,
we need to ensure that *ALL* input streams are blocked.
Failure to do so would result in having some input streams pushing data
to inactive elements (returning GST_FLOW_FLUSHING) or unlinked pads
(returning GST_FLOW_NOT_LINKED).
A later optimization could involve only blocking the input pads that
might be involved in reconfiguration. But better be safe than sorry for
now :)
Elements usually require that all fields on their caps are present
on the fixed caps they receive. Using intersection won't verify it,
resort to using is_subset() checks.
https://bugzilla.gnome.org/show_bug.cgi?id=760477
Those accept caps are actually checking if downstream supports
some particular caps to check if it need to negotiate a different
format. Checking only the next element with accept-caps is not enough
to guarantee that it is supported.
Using a caps query makes it obtain the supported caps for downstream
as a whole instead of only the next element.
Pass flags in _converter_new() so that we can configure ourselves
differently depending on some options.
SOURCE_WRITABLE -> IN_WRITABLE because the array is called 'in'
Simplify the API, we don't need the consumed and produced output
arguments. The caller needs to use the _get_in_frames/get_out_frames API
to check how much input is needed and how much output will be produced.
In this specific case it wouldn't cause problems as we only ever access the
first array element, but let's make explicit what is happening here.
CID 1346530 and 1346529
The filters' floating references are sinked during set_property() already,
which means that GstBin takes a new reference when adding the filter to it.
Get rid of the additional reference after adding the filter to the bin.
Unconditionally adding the template caps when proxying the caps query will play
havoc with decoders that attempt to choose an output format based on some caps
features. Creating a sink that does not include those caps features and a
decoder/parser/etc that preferentially chooses some specific caps feature when
available, will always return the decoder/parser/etc template caps and choose a
feature that downstream will be unable to support.
Fix by limiting the addition of the template caps to when the result is actually
empty.
https://bugzilla.gnome.org/show_bug.cgi?id=758212
This reverts commit 77dc09c3a9.
It can cause the FLUSH_START/STOP events to go to the sink elements, which
then causes state changes and various other problems. We shouldn't really
flush downstream here, the idea is to do *draining*.
Apart from that the testcase for the original bug here works without this
commit now.
Since the loops increasing count from 0 are always run at least
once (if count < 1), count will always be at least one when
compared to the drop/dup conditions.
Coverity 1139674
Add a property and logic to send a GstNetworkMessage event containing
the message that was received from a client. This can be used to
implement simply bidirectional communication.
Add a property and logic to send a GstNetworkMessageDispatched
event upstream to notify that a buffer has been sent. This can be used
to keep track of what client received what buffers.
Add a property to handle GstNetworkMessage events. These events contain
a buffer that is sent on the socket to allow for simple bidirectional
communication.
Otherwise we'll remove that element while keeping its buffering message in our
list, and because of that never ever report buffering 100% as that element
will always be at a lower percentage.
This fixes e.g. seeking over Period boundaries in DASH and various other
issues when buffering happens between group switches.
Also use a new mutex for protecting the buffering messages. The object lock is
already used by gst_object_has_as_ancestor() and we need to use it now for
checking if the buffering message sender has the to-be-removed element as
ancestor.
When we stop sending because we need more data, still keep a GSource
around to receive data from the clients.
Also handle read and write in the same go.
Make sure that any access to the GstDecodeBin's decode_chain
field is protected using the EXPOSE_LOCK. Also add a simple
reference counter to the GstDecodeChain structure so that when
the type_found signal fires it can hold onto the decode chain
even while the EXPOSE_LOCK is not held. This should fix a
race condition if the type_found signal fires right in the
middle of a state change that messes with the same decode
chain.
https://bugzilla.gnome.org/show_bug.cgi?id=755260
Just setting the ghostpad as flushing wasn't enough. It needs to be
consistent on the internal proxypad also, otherwise you end up in
situations where:
* a pending buffer on the target pad triggers the sticky event
propagation
* the default implementation sees that the proxypad is not flushing,
so it tries to push it to the other pad (the actual ghostpad)
* the ghostpad is flushing, so returns FALSE
* the push_event function sees that pushing the event failed...
* ... and pending buffer push returns GST_FLOW_ERROR, instead of
GST_FLOW_FLUSHING
By using gst_pad_set_active(FALSE), we ensure that both the ghostpad
and the proxypad are flushing/deactivated. The situation above will
no longer occur, and a GST_FLOW_FLUSHING will be returned.
Remove the format and layout from the mix_samples function and use the
format when creating the channel mixer object. Also use a flag to handle
the unlikely case of non-interleaved samples like we do elsewhere.
Add docs for the internal audioconvert object before moving it to the
audio library.
Remove get_sizes and implement the trivial logic in the element.
Remove some unused orc functions
Move the audio quantize code from audioconvert to the audio library.
work on making an audio converter helper function similar to the video
converter.
Fold fastrandom directly into the quantizer, add some ORC code to
optimize this later.
Rename _get_default_mask() to _get_fallback_mask() to make it more
clear that the function only provides a fallback if nothing else can be
done. Also clarify this in the documentation.
API: gst_audio_channel_get_fallback_mask()
In some conditions we might process empty buffers, calling
gst_control_binding_get_value_array in that case will lead
to the assertion:
(lt-ges-launch-1.0:18859): GStreamer-CRITICAL **: gst_control_binding_get_value_array: assertion 'values' failed
Add a TRUNCATE_RANGE flag for unpack functions to fill the least
significate bits with 0 (as did the old code). Also add functions
that don't truncate. Use the TRUNC flag in audioconvert for
backwards compatibility for now.
Use (1 << 31) as the multiplier for int<->float conversions. This makes
sure that int->float conversions always end up with floats between
[-1.0, 1.0].
For the conversion from float to int, this multiplier will give the complete
int range after we perform clipping.
Change the unit test to take this into consideration.
Fixes https://bugzilla.gnome.org/show_bug.cgi?id=755301
The client-removed signal used G_INT_TYPE instead of G_SOCKET_TYPE
in its definition leading to problems on platforms where the size
of a pointer is larger than the size of an integer, It would also
not work at all with dynamic language bindings.
https://bugzilla.gnome.org/show_bug.cgi?id=757155
Rewrite audioconvert to try to make it more clear what steps are
executed during conversion.
Add passthrough step that just does a memcpy when possible.
Add ORC optimized dither and quantization functions.
Implement noise-shaping on S32 samples only and allow for arbitrary
noise shaping coefficients if we want this later.
This makes sure that they will always get SEEK events, even if we're currently
in the middle of a group switch (i.e. switching to another
representation/bitrate/etc).
https://bugzilla.gnome.org/show_bug.cgi?id=606382
As stated in GST_PAD_PROBE_HANDLED's documentation, we are
supposed to unref the event before returning.
Fixes an event leak in the validate.hls.playback.play_15s.hls_bibbop
validate scenario.
https://bugzilla.gnome.org/show_bug.cgi?id=754459
Rework the converter to use the pack/unpack functions
Because the unpack functions can only unpack to 1 format, add a separate
conversion step for doubles when the unpack function produces int.
Do conversion to S32 in the quantize function directly.
Tweak the conversion factor for doing float->int conversion slightly to
get the full range of negative samples, use clamp to make sure we don't
exceed our int range on the positive axis (see also #755301)
Send event directly to playsink instead of letting GstBin iterate
over all sink elements. The latter might send the event multiple times
in case the SEEK causes a reconfiguration of the pipeline, as can easily
happen with adaptive streaming demuxers.
What would then happen is that the iterator would be reset, we send the
event again, and on the second time it will fail in the majority of cases
because the pipeline is still being reconfigured
The logic introduced by
[d50b713: decodebin: set the decode pad target before setting elements to PAUSED]
to expose pads would only ever be able to possibly expose one (the last) pad per element.
Make it so that any exposable pads are able to be exposed rather than just the
last pad returned by connect_element.
https://bugzilla.gnome.org/show_bug.cgi?id=742924
In the case of analyzing a demuxer chain, analyze_new_pad may create
a new GstDecodeChain. This was not propagated to the calling function which as
of [d50b713f decodebin: set the decode pad target before setting elements to PAUSED]
is now required to be able to expose the correct pad.
https://bugzilla.gnome.org/show_bug.cgi?id=742924
In case of reconfiguration, text_pad should be re-connected with
stream synchronizer sink pad. Otherwise we'll leave an unlinked pad around if
there always was a streamsynchronizer text pad.
https://bugzilla.gnome.org/show_bug.cgi?id=756804
Otherwise caps and context queries will disappear into nothing and therefore
fail. With autoplug-query now actually working, users (such as playbin) can
proxy these queries to the selected video sink and be able to select an
more appropriate configuration.
https://bugzilla.gnome.org/show_bug.cgi?id=731204
In case sink implements a streamvolume interface, volume element is being got
from the sink. But this is transfer full. So the memory should be freed before
setting it to NULL. This was resulting in major memory leaks
https://bugzilla.gnome.org/show_bug.cgi?id=755867
Allows to run such a command line :
gst-launch-1.0 uridecodebin uri=file:///home/meh/Music/sthg.mp4 ! \
encodebin profile-string="audio/x-wav|1" ! filesink location=sthg.wav
Previously the code failed because wavenc is considered as a muxer.
We still want encodebin to audio/x-wav as an AudioEncodingProfile,
so this simple fix allows that.
Ability to mux raw streams in containers such as matroskamux
is a different issue.
https://bugzilla.gnome.org/show_bug.cgi?id=751470
intersection with a downstream that accepts any video/x-raw caps
with no further detail won't create a framerate field. If it's
not in the caps, don't fixate it, just set it to 30/1
Casting to gpointer from gulong generates the following warning with
64bit Windows target MinGW:
gstplaybin2.c: In function 'pad_added_cb':
gstplaybin2.c:3476:7: error: cast to pointer from integer of different size [-Werror=int-to-pointer-cast]
(gpointer) group_id_probe_handler);
^
cc1: all warnings being treated as errors
We should cast to guintptr from gulong before we cast to gpointer.
https://bugzilla.gnome.org/show_bug.cgi?id=754755
The default one will just go through the internal elements which might
just be identity when it is in passthrough which will lead to the query
being handled by the downstream sink, ignoring all that playsinkconvertbin
could actually handle and convert.
https://bugzilla.gnome.org/show_bug.cgi?id=754235
It's only relevant for each group, and by storing it in the group
we have locking and everything else like for the other buffering-related
variables. Locking looks a bit fishy still, but it was like that for a long
time already so shouldn't be worse than before.
Overview:
There are some of interleaved streams which has long-term location of audio data.
It mean the audio data is located far away more than multiqueue size.
In this case, because of multiqueue overrun, the pipeline is stopped.
To prevent hanging-like state, the decodebin needs to handle the queue size.
Caused:
The multiqueue size is not enough, the pipeline will stay being stalled status
and decodebin cannot complete to build decode chain.
In this issue file, decodebin did not receive no_more_pads signal or audio data yet.
Steps to Reproduce:
play the high-resolution(4K file) files or some streaming media(push mode).
Actual Results:
There is no audio or subtitle.
We can see only video or infinite loading.
Resolution:
Decodebin detect this problem, and add extra buffer size to multiqueue.
The multiqueue is larger than before, the next data can be pushed the downstream element.
Additional Information:
The max-preroll extra buffer size is set 8MB.
We can use total pre-roll buffer 10MB.
Only first overrun callback can handle multiqueue size.
https://bugzilla.gnome.org/show_bug.cgi?id=733235
When an upstream element wants to flush downstream, we need to take
all chains/groups into consideration.
To that effect, when a FLUSH_START event is seen, after having it
sent downstream we mark all those chains/groups as "drained" (as if
they had seen a EOS event on the endpads).
When a FLUSH_STOP event is received, we check if we need to switch groups.
This is done by checking if there are next groups. If so, we will switch
over to the latest next_group. The actual switch will be done when
that group is blocked.
https://bugzilla.gnome.org/show_bug.cgi?id=606382
When upstream events/queries reach sinkpads of unlinked groups (i.e.
no longer linked to the upstream demuxer), this patch attempts to find
the linked group and forward it upstream of that group.
This is done by adding upstream event/query probes on new group sinkpads
and then:
* Checking if the pad is linked or not (has a peer or not)
* If there is a peer, just let the event/query follow through normally
* If there is no peer, we find a pad to which to proxy it and return
GST_PROBE_HANDLED if it succeeded (allowing the event/query to be properly
returned to the initial called)
Note that this is definitely not thread-safe for the time being
https://bugzilla.gnome.org/show_bug.cgi?id=606382
When we see prefix NALs before a Subset SPS has been spotted,
it might just be because the stream was truncated at the
start, so don't count those as either 'bad' or 'good' packets.
Since the videorate element just duplicates or drops frames
to achieve the desired framerate, it can accept video/x-bayer media
(in any format), which are not present in the current caps.
Just add "video/x-bayer(ANY);" to the caps of the static pad template
(fixing line style to pass the indent commit hook).
https://bugzilla.gnome.org/show_bug.cgi?id=753483
deadend_details need not be returned when the pad is not a deadend.
Hence checking if res value is TRUE and clearing the string instead of
passing it on
https://bugzilla.gnome.org/show_bug.cgi?id=753088
Add logging categories for most video objects.
Remove some useless debug lines in video-info and videotestsrc.
Add a performance debug line in the video scaler.
When switching to a new chain it might be that this new chain
is not yet ready to be exposed so check it before exposing.
Can happen with mpegts that might delay adding pads or pushing data
until it has found the PMT/PAT/PCR and that may take a while depending
on the stream.
It happened frequently with HLS:
http://vevoplaylist-live.hls.adaptive.level3.net/vevo/ch1/appleman.m3u8
If the sink has properties named volume and mute, we have no idea about their
meaning. The streamvolume interface standardizes the meaning.
In the case of osxaudiosink for example, the current volume property has a
range of 0.0 to 1.0, but we need 0.0 to 10.0 or similar. Also osxaudiosink
has no mute property. As such, the volume element should be used here instead.
https://bugzilla.gnome.org/show_bug.cgi?id=752156
Have all sections in alphabetical order. Also make the macro order consistent.
This is a preparation for generating the file. Remove GET_CLASS macro for
some elements, since it is not used and the header is not installed.
We reset the group start time to the running time of the start of the other
streams that are not flushed. This fixes seeking in gapless mode after the
first track has played.
https://bugzilla.gnome.org/show_bug.cgi?id=750013
If suburidecodebin is failed to negotiate (e.g file does not exist)
then free internal suburi variable so that 'current-suburi' property
returns correct status.
https://bugzilla.gnome.org/show_bug.cgi?id=751118
6a2f017bfa changed it to check the subtitle
factory caps if there is a text-sink but we fail to get its sinkpad. What
actually should be done here is to use the factory caps if there is no
text-sink at all.
https://bugzilla.gnome.org/show_bug.cgi?id=750785
There is the GstVideoMultiviewMode enum and the
GstVideoMultiviewFramePacking, which is a subset of the
multiview modes, with the same values as the corresponding
types from the full enum. Do some casts and use the right
times to avoid implicitly using/passing GstVideoMultiviewFramePacking
when a GstVideoMultiviewMode is needed.
Add GstVideoMultiviewFramePacking enum, and the
video-multiview-mode and video-multiview-flags
properties on playbin.
Use a pad probe to replace the multiview information in
video caps sent out from uridecodebin.
This is a part implementation only - for full
correctness, it should also modify caps in caps events,
accept-caps and allocation queries.
https://bugzilla.gnome.org/show_bug.cgi?id=611157
When traversing the color balance element channel list to find the one that
matches with the playsink proxy, the assignation was set to iterator of the
playsink proxy, not the balance element. Thus, the mapping to the values of
the balance element channel was wrong.
This patch fixes the assignation of the color balance element channel, so the
mapping to the channel of the color balance element is fixed.
https://bugzilla.gnome.org/show_bug.cgi?id=750691
when text playbin is not enabled in the beginning, then
video_srcpad_stream_synchronizer gets linked to videochain->sinkpad
and when we try to enable text bin during play, since it is already linked to videochain,
text chain does not get linked properly. Hence unlinking the same
before linking to text chain
https://bugzilla.gnome.org/show_bug.cgi?id=748908
Summary:
So that the user can easily use the same encoding profile to render
with/without audio/video stream.
API:
gst_encoding_profile_is_disabled
gst_encoding_pofile_set_enabled
https://bugzilla.gnome.org/show_bug.cgi?id=749056
When a stream has a variable framerate, videorate calculates it and
forces it on the output caps. However, the code in _transform_caps()
currently also does that if the transform is going in the opposite
direction (GST_PAD_SRC), so during a renegotiation it tries to force
upstream to use the calculated framerate and it fails.
https://bugzilla.gnome.org/show_bug.cgi?id=750032
This part of pipeline is:
tee name=t ! visualizationbin ! streamsynchronizer name=s
t. ! s.
streamsynchronizer might block and it could starve the visualization
branch of the pipeline when it is enabled.
The visualization bin has queues internally but the other branch
that links the audiotee directly to the synchronizer is vulnerable
to block. Adding a queue between "t. ! s." fixes deadlocks.
https://bugzilla.gnome.org/show_bug.cgi?id=749676
From the API documentation: "Note that it is generally not
a good idea to reuse an existing cancellable for more
operations after it has been cancelled once, as this
function might tempt you to do. The recommended practice
is to drop the reference to a cancellable after cancelling
it, and let it die with the outstanding async operations.
You should create a fresh cancellable for further async
operations."
https://bugzilla.gnome.org/show_bug.cgi?id=739132