我们知道,UDP它不关心分段(数据包)按顺序到达目的地。那么我们如何YouTube或VoIP (skype) 能够流式传输视频?
如果一个数据包丢失(没有到达目的地),目的地对此一无所知。所以,它不能要求目标重新传输它。并且由于无连接性,UDP不一定所有段都按顺序到达目的地。
如果某个片段乱序到达,则流式传输的视频不应该失真吗?因为现在整个段的顺序是错误的,因为一个段不在它的位置上或者数据包乱序。
我们知道,UDP它不关心分段(数据包)按顺序到达目的地。那么我们如何YouTube或VoIP (skype) 能够流式传输视频?
如果一个数据包丢失(没有到达目的地),目的地对此一无所知。所以,它不能要求目标重新传输它。并且由于无连接性,UDP不一定所有段都按顺序到达目的地。
如果某个片段乱序到达,则流式传输的视频不应该失真吗?因为现在整个段的顺序是错误的,因为一个段不在它的位置上或者数据包乱序。
实时应用程序并不关心按顺序接收,而是关心及时交付 = 低延迟。粗略地说,只有一个明确的、小的时间窗口,数据是有用的。迟到的数据根本没用。
如果数据丢失,您可能会在视频(或音频)中出现小故障,但剪辑会继续运行(= 该应用程序旨在处理丢失的数据并充分利用它)。重新传输丢失的数据甚至是不可取的,因为您需要暂停视频/音频,直到重新传输的数据到达。在播放预先录制的视频剪辑时,这甚至可能是一种选择,但绝对不能用于视频或音频会议。
使用 TCP 的按顺序(但可能会延迟)交付具有完全相同的问题。
当然,应用程序需要注意标记它的数据报,以便它知道它当前接收到的数据用于什么目的。不幸的是,这到底是如何工作的在这里是题外话。
无论如何,面向连接或无连接的 L4 协议的问题是次要的。如果您使用的传输层协议(通常是 UDP)还没有提供连接概念,您可能需要在应用层上创建这样一个概念(大多数应用程序可能都需要)——但这不是主题也是。
简短回答:多媒体在 UDP 之上实现协议。它们实现了所需的功能。实际上,它们具有更多的功能,并且比 TCP 更复杂。
简短的答案:请参阅@Zac67 的答案。
长答案:我希望下面的文字能让您对这个问题有更好的理解。
首先,我们需要区分不同类型的多媒体。是否有预录视频流(例如,YouTube)或实时交互式对话(例如,Skype)是很重要的。我称它们为实时多媒体。还有直播(例如twitch),但我不熟悉。
TCP 非常适合传输 YouTube 视频。YouTube 会采取一些措施来确保您不会真正看到是否有重新传输。
基本上问题是我们必须围绕以下生活事实进行游戏:
理想情况下,多媒体系统应具有低于 200 毫秒的口对耳延迟,以使人感到舒适。嘴对耳延迟超过 400 毫秒,人脑不认为对话是交互式的。
这适用于每个用于人们通话的系统——电话、手机等。
请注意,口对耳是指从您说话的时间到您的话在另一边的扬声器上播放的时间。这不仅包括网络延迟。
因此,基本上,多媒体协议的目标之一就是解决这个限制。
让我们看看当一个数据包丢失时会发生什么,但后续数据包可能会到来。TCP 需要按顺序传送数据包。因此,TCP 在内部缓冲后续数据包,同时向源发送数据包丢失的信号。一旦丢失的数据包被传递,所有后续数据包也被传递。这称为行头阻塞。
实时多媒体的问题实际上是这种重传会导致延迟>400ms。我们处理丢失数据包的方式也需要这些后续数据包。因此 VoIP 不能使用 TCP。
好吧,我们没有使用 UDP,我们正在设计在 UDP 之上工作的协议。UDP有端口。除了端口,UDP 提供与 IP 相同的服务。我认为我们可以有一个不同的传输协议而不是 UDP,而不是在它之上。我不知道为什么以及为什么不这样做的任何原因,除了从数据包标头的开销来看,这并不重要。
好的,重传不是一种选择。但是我们必须以某种方式处理丢失的片段。
基本上,我们有两个选择。选项 1 是在流中包含“冗余”(发送额外的数据包),选项 2 是利用语音/视频流的属性来近似重建数据(“插值”)或更精确地向人类展示一些可行的东西,而不是丢失的数据包。AFAIK 多媒体流将两者结合起来。
这个想法是发送方发送额外的数据包,如果一个数据包丢失,这些额外的数据包可用于重建丢失的数据包。
这种功能的一个示例是一类称为前向纠错(FEC) 的方法。非常基本的 FEC 方案的工作原理如下。发送者必须发送 p1、p2、p3 和 p4。然后它构造并发送一个 FEC 数据包 p5 = p1 xor p2 xor p3 xor p4。如果接收方接收到这 5 个数据包中的任何 4 个,它可以将 p1 重构为 p4。有更复杂的选项可以处理多个数据包丢失。
请注意,FEC 允许您处理一些丢失的数据包。无法保证在某个时候丢失的数据包会比预期的多。如果发生这种情况,仍然需要另一种方法。
语音和视频数据通常在不同的数据包之间有很多相似之处。或者更好地说——人的眼睛和耳朵并不那么挑剔。例如,如果您说 hllo 或 hllo 而不是 hello,大多数人都会理解。(我认为一个数据包小于一个声音。)如果您正在观看 25 fps 的视频,并且缺少一帧,您可能根本不会注意到它。因此,接收方可以通过多种方式处理丢失的数据包,例如重放前一个数据包(视频),或者在前一个数据包和下一个数据包之间进行一些插值。
是的,这意味着接收器上的流可能与发送器上的流不同。多媒体流可以容忍这一点。
请注意,即使插值失败,人类仍然可以请求重新传输,也就是“你能重复一下吗”、“我没听到你说什么”等等。当然,如果这种情况一直发生,系统将无法使用,但如果这种情况很少发生,那也没关系。
或者为什么 YouTube 可以使用 TCP?
不同的是没有 200ms/400ms 的延迟要求。在发送数据包、接收该数据包和播放该数据包中的音频/视频片段之间没有严格的延迟。这就是为什么我们只是为了方便而使用 TCP,但改变应用程序来解决这个延迟。
YouTube 视频是预先录制的。您可以以网络允许的速度传输它们。理想情况下,这比播放速度更快。
此外,视频可以(我认为)预缓冲。在播放第一帧之前,当缓冲区中有例如 5 秒的视频时,您可以开始播放视频。因此,如果有丢包,则播放器有 5 秒的视频要显示,此时数据包将被重新传输。如果 5 秒太短,则可以增加。
注意:实时多媒体也使用类似的缓冲区,因为所谓的抖动(数据包到达间隔的变化),这里没有涉及。但由于 200 毫秒的延迟限制,此缓冲区在进入扬声器/显示器之前只能包含几毫秒的数据。