RFC5077 TLS Session Resumption without Server-Side State

概述 这篇 RFC 废弃了 "RFC4507: Transport Layer Security (TLS) Session Resumption without Server-Side State" 主要描述了在不需要维护服务器状态的情况下如何重启一个 TLS Session 状态总归是要有的, 比如加密套件, 加密的主密钥, 它们都保存在一个由服务器知道的密钥加密过的一个 ticket 里 it stores its session state (such as ciphersuite and master secret) to a ticket that is encrypted and integrity-protected by a key known only to the server. The ticket is distributed to […] →Read more

失业意味着什么

现在经济环境糟糕, 政治环境不可说,看不到未来的希望,公司刚刚经历大裁员,失业的老同事找工作很难, 年龄越大,机会越少。 失业对我意味着什么呢? 没有收入, 没有施展平生所学的舞台,失去自信,尊严受到了打击。 可是我还是我, 我自己没做错什么, 没有必要惩罚自己,反而要相信自己天生我材必有用, 千金散尽还复来。 中国的互联网界很奇怪, 程序员35岁似乎就感觉岁数太大了,不适合在这行工作了, 而我已经年过四十,年近半百,在大多数互联网公司, 这么大岁数的程序员差不多绝迹了。现在即使顶个 Tech Leader 的 title, 做的还是一线设计和编程,我也乐此不疲,虽然也常常给难搞的 bug 折磨。 如何未来有一天我失业了, 我不知道该去做什么, 写书,翻译,或者去家小公司打工,或者去跑外卖, 我不知道,我只知道自己不可能在家歇着啥事不干,这既不是我的作风, 也不符合我们家的家风,母亲曾经在工厂发不出工资的窘况下,一边独自抚养我们兄弟, 一边兼职做各种小生意,卖过水果,矿泉水,报纸等等。 我是我妈的儿子,我也是打不垮的小强,我能在这浊世自处,为家人撑起一片天。 只是当下的时光里, 我需要做点什么未雨绸缪的事情呢? →Read more

韭菜的自白

自从卖了旧房子,买了处新房子, 我感觉自己就象一棵韭菜, 任由中介,开发商,装修公司尽情收割。 我则彻底躺平, 任由别人收割, 并不知道如何保护自己, 程序员的世界中,一是一,二是二, 黑是黑, 白是白,哪里知道人世间的尔虞我诈, 相互算计,只觉得厌烦, 大的方向不要欺瞒过分,超越底线, 让他们赚该赚的钱,我自己省点心去学点新知识,读个新学位,或者写本新书 →Read more

芙蓉道楷

一法原无万法空 个中哪许悟圆通 将谓少林消息断 桃花依旧笑春风 →Read more

WebRTC 快速测试

搭建测试环境 启动测试程序 git clone git@github.com:walterfan/webrtc_video_chat.git cd webrtc_video_chat ./start.sh 启动浏览器 cd /Applications/Google\ Chrome\ Canary.app/Contents/MacOS/ ./Google\ Chrome\ Canary –disable-webrtc-encryption Chrome 有些 WebRTC 相关的测试开关很有用 –allow-file-access-from-files allows getUserMedia() to be called from file:// URLs. –disable-gesture-requirement-for-media-playback removes the need to tap a <video> element to start it playing on Android. –use-fake-ui-for-media-stream avoids the need to grant camera/microphone permissions. –use-fake-device-for-media-stream feeds […] →Read more

活文档-知识从哪来

知识从哪里来 读书 上课 开会 聊天 实验 观察 有些知识一成不变, 有些知识天天在变, 所以需要与时俱进. 为什么需要知识 我们要解决问题, 需要知识来清楚地发现问题, 定义问题, 分析问题, 最终解决问题. Peter Naur 写了一篇论文 "Programming as theory Building" – 以理论构建来编程. 程序设计是集体智慧的结晶, 与其说是告诉电脑该做什么, 不如说是与其他开发人员分享那些通过学习,实验,对话和深刻的反思而精心阐述过的理论和模型 正确的编程应该看作这样一种活动, 程序员通过其形成或获取的对当前问题的某种见解通过代码实现满足需求. 我们通常重视读书和上课来获取知识, 而忽略了聊天, 实验和观察来学习和产生知识. 而文档就是将有价值的知识传递给当前以及未来的人的过程. 文档是为了传递有价值的知识, 价值不大或众所周知的知识不值得写成文档 只有长期令人感兴趣的知识才值得被写成文档 只有令很多人感兴趣的知识才值得被写成文档 有价值或重要的知识也可能需要被写成文档 →Read more

文档的反模式

在一般人眼里, 文档是个很无聊的东西, 写了很多无用的东西, 在产品线上用不着. 最要命的是, 它的目的是帮助理解, 可是经常会由于没有及时更新而误导读者. 中国有句俗语,好记性不如烂笔头,现代世界纸笔已经无需烂笔头了,但是一样的道理,人的大脑会遗忘很多东西,需要用文档来记录和分享有价值或重要的知识。 Gojko Adzic 的 “实例化需求:团队如何交付正确的软件” 一书中描述了执行 BDD(行为驱动开发) 的团队编写的需求说明和测试用例非常有用。 由于测试自动化,只要测试全部通过,这个文档就会始终保持最新。这种文档就是活文档。 在图书馆看到一本书 活文档 与代码共同演进,作者是法国人西里尔·马特雷尔(Cyrille Martraire)。 英文书名 – "Living Documentation: Continuous Knowledge Sharing by Design". 随手翻了翻, 记录一些要点 文档的反模式 独立的活动 文档与编码, 测试及部署之间没有紧密结合在一起 需要手工转录 冗余的知识 如果所有的知识都能在代码中找到, 那么文档又有什么用呢? 无聊的时间陷阱 写文档会花费很多时间, 而花的时间与人与己往往并不划算 脑转储 只是将脑中所想的东西写下来, 没有组织和提炼, 想到什么就写什么, 读起来用处不大且费劲 优美的图表 一图胜千言, 问题在于图表要有引人注目的说服力和生命力 迷恋符号 UML 及专有符号的滥用, 让人陷入到细节中 不用符号 […] →Read more

音视频的同步

音视频同步可检测到的阈值在 +45ms 到 -125ms 之间, 可接受的阈值平均约为 +90ms 到 -185 ms, 正值表示声音相对于图像超前多少 在 T-REC-G.114-200305 中总结到: ~280ms 有些用户不满意 ~380ms 许多用户不满意 ~500ms 几乎所有都不满意 延迟来自哪里, 可以看看音视频各自的流程 音频处理流程 延迟可能来自如下步骤 从设备捕获音频的延迟 输入音频处理的延迟 3A 音频编码的延迟 网络传输的延迟 抖动缓冲的延迟 音频解码的延迟 音频输出处理的延迟 从设备输出到耳朵的延迟 视频处理流程 WebRTC 中有相关的度量 estimatedPlayoutTimestamp of type DOMHighResTimeStamp This is the estimated playout time of this receiver’s track. 这就是接收的音轨估计的回放时间 The playout time is […] →Read more

H.264 packetization types

在视频会议中 H264 的 NAL: Network Abstraction Layer 包类型基本上有三种 1) Single NAL unit 单个 NALU 2) STAP-A: Single Time Aggregation Packet 单时间聚合包 3) FU-A: Fragmentation Unit Packet 片段单元包 // The packetization types that we support: single, aggregated, and fragmented. enum H264PacketizationTypes { kH264SingleNalu, // This packet contains a single NAL unit. kH264StapA, // This packet contains […] →Read more

WebRTC Bandwidth Allocation

Title Bandwidth allocation by REMB ModuleRtpRtcpImpl->RTCPReceiver: IncomingPacket RTCPReceiver->RTCPReceiver: TriggerCallbacksFromRtcpPacket RTCPReceiver->RtpTransportControllerSend:OnReceivedEstimatedBitrate(bitrate) RtpTransportControllerSend->GoogCcNetworkController: OnRemoteBitrateReport(receiveTime, bitrate) GoogCcNetworkController->SendSideBandwidthEstimation: UpdateReceiverEstimate SendSideBandwidthEstimation->SendSideBandwidthEstimation: ApplyTargetLimits SendSideBandwidthEstimation->SendSideBandwidthEstimation: UpdateTargetBitrate #SendSideBandwidthEstimation->LinkCapacityTracker:OnRateUpdate GoogCcNetworkController->Call: OnTargetTransferRate Call->BitrateAllocator: OnNetworkEstimateChanged BitrateAllocator->BitrateAllocator: AllocateBitrates Snippets AllocateBitrates 带宽分配方法 std::map<BitrateAllocatorObserver*, int> AllocateBitrates( const std::vector<AllocatableTrack>& allocatable_tracks, uint32_t bitrate) { if (allocatable_tracks.empty()) return std::map<BitrateAllocatorObserver*, int>(); if (bitrate == 0) return ZeroRateAllocation(allocatable_tracks); uint32_t sum_min_bitrates = 0; uint32_t sum_max_bitrates […] →Read more