weekly of 20180617

工具技巧

  • 写好shell脚本的13个技巧 : 很多建议都非常中肯,有点琐碎,去能真正提供好用户体验, 具体如下(个人感觉最后有一个shell的lib自动提供如下的能力) :
    1. 提供–help标记
    2. 检查所有命令的可用性
    3. 独立于当前工作目录
    4. 如何读取输入:环境变量 vs. 标记
    5. 打印对系统执行的所有操作
    6. 如果有必要,提供–silent选项
    7. 重新开启显示
    8. 用动画的方式显示进度
    9. 用颜色编码输出
    10. 出现错误立即退出脚本
    11. 自己执行清理工作
    12. 在退出时使用不同的错误码
    13. 在结束时打印一个新行
  • Meet the GitLab Web IDE : 介绍Gitlab的web IDE背后设计的思路和发展历程,整体感觉集Web IDE集成在gitlab可以对开发流程提供的想象空间很大

  • Carbon : “Create and share beautiful images of your source code”, 其可以生成渲染出好看的代码截图(不知道有什么用~)

系统设计

  • Caching beyond RAM: the case for NVMe : 本文提供了一个memcached的新的解决方案,通过exstore机制,将部分缓存的value数据存储在独立的存储引擎上面(比如SSD或者本文的NVMe存储介质),数据表明,其性价比和性能还是非常可观的, 其中的Extstore值得关注

  • Twitter meets TensorFlow : mark, 介绍twitter的tensorflow的接入历程

  • Accelerate large-scale applications with BOLT | Engineering Blog | Facebook Code : 现在多数软件系统的体积都会很大,这可能会导致其不能被CPU cache命中,进而会导致诸如Instruction Starvation的问题, 所以Binary Optimization and Layout Tool就有一定的发展空间;本文介绍了Facebook的BOLT的解决方案, 其通过链接优化,profile采集进而进行二进制优化,来提升整体程序的性能,支持多种CPU架构和编译器,可以感觉Facebook在基础技术的优化做的还是非常精细的

专题topic

其他

weekly of 20180610

工具技巧

系统设计

  • How Instagram’s algorithm works | TechCrunch : 本文介绍Instagram的新的排序算法,其相比于传统的基于回复时间排序的算法,对于文章的曝光率有了明显的提升,具体策略算法方面,只是介绍了一些核心的思路,细节之处没有做过多介绍,但是仍旧值得关注。

  • 重新理解微服务 : 感觉相对来说比较干货的文章,具体介绍了业务服务化改造后可能面临的问题,以及其解决方案,重点介绍了”服务粒度”, “服务组合”, “数据一致性”, “支撑系统” 等一些基础设施以及能力在落地时候的关键点

  • The End of Video Coding? – Netflix TechBlog – Medium : 一个反问的标题,其实对视频的编码技术的优化需求从来没这么迫切,随着视频时代到来,如果在有效带宽上面提供更好的用户体验一直是各厂商的需求,作者踢了几点思路,感觉可以参考:

    • Let’s innovate beyond block-based hybrid encoding
    • The community needs better ways to measure video quality
    • Encouraging new ideas means discussing with new people(这个忽略)

专题topic

其他

weekly of 20180520

工具技巧

  • 2018-05-16-bbr : 对TCP的BBR的拥塞机制的系统介绍和说明

  • How JavaScript works: A comparison with WebAssembly + why in certain cases it’s better to use it over JavaScript : 比较精炼的介绍了Web Assembly相比于Javascript的优势,以及其实现机制,一些配图都挺赞的, 而且blog里面的How Javascript works也挺赞的,可以关注

  • Tearing apart printf() – MaiZure’s Projects : 一个简单的printf的调用其底层实现机制具体的怎么样的呢? 作者通过strace/gdb等一系列工具,详细说明了printf实现机制,包括静态/动态链接是,其在C标准库, 系统调用方面的情况, 是很好的了解系统编译,链接机制的教材

  • stdio buffering : 文章介绍,在Shell环境下,由于输入/输出,pipe都会有一定的内存buffer, 可能会导致一些程序有非预期行为(输出不及时等),其通过图例直观的展示了buffer的影响,同时概述的介绍一些linux后续可以考虑采纳的方案,比如通过引入BUF_1的环境变量, 引入stdbuf等命令

系统设计

专题topic

其他

weekly of 20180413

工具技巧

系统设计

专题topic

其他

weekly of 20180505

延庆

工具技巧

  • SSH client configuration tricks : 关于SSH的使用技巧, 可以对特定机器设定alias, 并且绑定相关配置, 对于常见的VPS可以做这类的优化

  • CPU utilization is wrong, says Netflix’s Brendan Gregg : 关于CPU优化的深入讨论, 其实强调的核心理念是,现在CPU和内存的速度越差越大,所以有时候会我们发现CPU idle很低的时候,有可能其并不是在忙着执行指令,而是在等待Memory IO,尤其是高速缓存失效的时候

  • online binary tools : 一些online bianry的工具集合, 有兴趣可以关注下。不过个人更喜欢用类似于Zeppelin通过此类的平台,来构建自己的工具集

  • Elasticsearch-基础介绍及索引原理分析 : 对ES的索引和存储架构有比较详细的说明,可以快速了解下

  • google/randen: Fast backtracking-resistant random generator : “What if we could default to attack-resistant random generators without excessive CPU cost? We introduce ‘Randen’, a new generator with security guarantees; it outperforms MT19937 and pcg64_c32 in real-world benchmarks. This is made possible by AES hardware acceleration and a large Feistel permutation.”, Google提出的新的随机数生成器,不过对其要解决的问题和解决的方案并不是很了解,先mark

系统设计

专题topic

这两周主要关注WebAssembly,在整理相关的文章~

其他

weekly of 20180429

工具技巧

系统设计

专题topic

其他

weekly of 20180422

中超现场

工具技巧

  • Facebook Container for Firefox : Firefox发布了一个支持自动隔离facebook的扩展, 其实现在的feed机制也一直在窃取各种个人信息,mark后续研究下,在国内互联网,这类的数据是如何传播传递的,同时又如何可以避免~

  • GraalVM : “GraalVM is a universal virtual machine for running applications written in JavaScript, Python, Ruby, R, JVM-based languages like Java, Scala, Kotlin, and LLVM-based languages such as C and C++”, Oracle出品的,意在构建一个统一的VM,看其文档,应该包括对整个编译链的支持(比如支持定制化构建自己的语言),先mark关注

  • FFmpeg 4.0 released : 最新版的FFmpeg好像有不少新的功能

  • Mermaid: Markdown-like generation of diagrams and flowcharts from text : 有点类似于Dot语言的规则模式,不过其在生成图片的配色方面更好看一些,不过整体图片的布局还是需要进一步的优化,其也被gitlab所支持

系统设计

专题topic

其他

  • The Missing Building Blocks of the Web : 现在互联网的一切好像都是理所当然的,比如中心化的服务交付,基于js/css等技术组合的web页面, 作者的这个系列从不忘初心开始, 讨论早期互联网技术的设计偏好,以及研究其在发展历程中间的演变,最后分析以后互联网技术发展的方向,同时可以关注的文章还有It’s time to rebuild the webThe Web We Lost

  • Probability Theory (For Scientists and Engineers) : mark

  • Unwinding Uber’s Most Efficient Service : mark

  • 机器学习宗师迈克尔·乔丹:AI革命尚未发生 : 作者认为,技术变更的本质是『在保证安全的前提下,为人们带来新的资源和能力』,所以我们系统更系统宏观的考虑现实世界的问题,AI(或者文中所说的IA),会是我们构建更理想目标世界(II(Intelligent Infrastruction))的一个强有力的工具手段,但是不会是全部,而且也很难奢望通过AI等就能自动学习构建更理想的社会。另一方面,从II的视角去考虑问题,可能会更快的触达本质。以自动驾驶为例,我们现在的从IA(AI)的角度,核心的注意力在于让汽车去拥有人的判断力;但是从II的角度,去构建一个更高效的交通体系,其会自动化控制所有汽车,通过大规模的物联网,机器学习算法去做调度控制,可能是一个更好的选择(这段纯属自己臆想)。

  • InnoDB 存储引擎原理解析 : 关于Innodb的介绍,不过是纯PPT版本,有些内容只看图片并不直观

  • 关于Pornhub的一些产品细节和道德节操 : 挺有意思的一个说明, Maybe只有压力没那么大的一些产品,对于用户体验和产品细节才会如此用心

PAC文件

概述

PAC文件(Proxy Auto-Config)可以约定浏览器如何去访问一个特定的网站。其应该是最为常见的代理技术之一,以其方便,简洁,灵活性被大部分主流系统(无论是安卓还是IOS)和浏览器所支持。正好最近处理了一个PAC的问题,所以这里具体介绍PAC相关的技术,包括PAC的文件编写和PAC的代理技术。

PAC文件编写

如上,PAC是一个用来约定浏览器如何访问网站的配置描述。其组织方式如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
//code demo from: https://en.wikipedia.org/wiki/Proxy_auto-config
function FindProxyForURL(url, host) {
// our local URLs from the domains below example.com don't need a proxy:
if (shExpMatch(host, "*.example.com"))
{
return "DIRECT";
}
// URLs within this network are accessed through
// port 8080 on fastproxy.example.com:
if (isInNet(host, "10.0.0.0", "255.255.248.0"))
{
return "PROXY fastproxy.example.com:8080";
}
// All other requests go through port 8080 of proxy.example.com.
// should that fail to respond, go directly to the WWW:
return "PROXY proxy.example.com:8080; DIRECT";
}

其核心是暴露一个FindProxyForURL的接口,每次有请求时候触发这个函数的回调,用于判断具体走哪种方式。 具体编写应用时,有如下几点可以注意:

  • url/host信息 : 如果请求是https协议,则回调的url里面并不会包含完整路径信息, 也就是说如果原始的url是https://xyz.com/abc回调给FindProxyForURL的参数也只是https://xyz.com, 这就意味着对于https协议,我们做不了url粒度的代理控制。具体可以参考Full URLs for HTTPS are no longer provided to PAC scripts

  • 调试问题: PAC的调试和普通js的调试有点不一样,其是浏览器自动触发请求的,所以方法也有些区别。在Chrome环境下,可以去chrome://net-internals/#proxy用于重新加载代理脚本, 同时在chrome://net-internals/#events去追踪日志,详细可以参考How to debug proxy.pac with Google Chrome

  • 代理问题 : 无论是怎么样的代理策略,最终我们函数需要返回的是一个代理服务器, 现在主流的浏览器主要支持如下三种访问方式:

指令类型 方式
DIRECT 直接访问
PROXY name:port 通过走特定地址的http代理访问
SOCKS name:port 通过走特定地址的socks代理访问

具体实现的时候也可以通过不同协议的组合或者冗余,来提供更高质量的代理服务。

这里我们重点关注PROXY name:port的方式,其提供的是一个HTTP代理访问的能力支持, 我们现在主流有http/https两个访问协议,其又具体如何去实现代理的呢?

HTTP代理

如上,我们希望通过一个http/https服务来提供对http/https访问的代理。如果是仅仅代理HTTP访问, 其实算比较简单。由于是纯文本,也无需任何鉴权之类的逻辑(TLS),只有正常转发请求即可,普通的Nginx就能实现该功能,可以参考nginx与https:正向代理支持(原文有些地方有错误之处)。但是如何基于http/https的服务做https的代理呢? 因为对服务器的验证等不可能是代理服务器自己实现的,故而需要代理服务器,根本上面支持TLS或者更底层的服务代理。

这里需要用到HTTP tunnel技术, 其主要包括两个步骤:

  1. 协商阶段: 这个时候Client发送一个CONNECT指令,连接代理服务器,同时告诉代理服务器具体要访问的地址, 具体如下:
1
2
3
4
5
6
## Client发送CONNECT指令
CONNECT example.host.com:22 HTTP/1.1
Proxy-Authorization: Basic encoded-credentials
## 服务器返回OK,这这次协商完成,允许代理
HTTP/1.1 200 OK

如上其实是一个正常标准的HTTP交互流程

  1. 代理阶段 : 一旦协商OK,代理服务器这个时候有点类似于要转变成TCP代理,只做透明的client和server之间的数据转发

可以通过一个wireshark的请求包,来进一步了解给过程:

HTTP tunnel

HTTP代理实现

从HTTP代理的协议我们可以知道,如果一个服务器要实现HTTP tunnel代理既要支持HTTP的CONNECT指令,也得支持TLS或者TCP的代理。这个要求对于之前的nginx是很难实现的,所以大部分的解决方案都是基于squid,当然我们知道通过ngx_http_proxy_connect_module也能实现,但是需要打上patch包,维护成本相对较高。

那有没有可能用更便捷的方式,让Nginx实现HTTP tunnel代理呢?答案是肯定的!

我们知道Nginx已经通过ngx_stream_core_module, ngx_stream_proxy_module等模块这次了TCP/UDP的代理,加上openresty/stream-lua-nginx-module的支持,我们可以很方便的去实现上面的代理协议。整体思路如下:

  1. 应用nginx的stream能力,做TCP的透明代理
  2. 对于初次建立链接的请求,做一些包体的分析,如果是CONNECT方式,则以HTTP方式返回数据,构建协商协议
  3. 协商之后,则以TCP代理方式提供服务即可

整体代码配置如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
stream {
log_format basic '$remote_addr [$time_local] '
'$protocol $status $bytes_sent $bytes_received '
'$session_time';
## 需要声明一个变量,注意该指令在stream-lua-nginx-module-0.0.4版本以上才有
lua_add_variable $py_upstream;
server {
listen 7070;
access_log logs/stream.log basic;
## 指定dns解析代理服务器
resolver 8.8.8.8;
## preread_by_lua是在每次连接建立(TCP)或者数据包(UDP)过来被触发调用
## 代码无太多容错性,仅用于描述功能
preread_by_lua_block {
local sock = assert(ngx.req.socket(true))
## 获取数据
local data = sock:receive()
local len = string.len(data)
local connect = string.sub(data,1, 7)
## ngx.log(ngx.ERR, "data is: ", data)
## 判断前缀是不是"CONNECT"
if connect ~= "CONNECT" then
ngx.log(ngx.ERR, "prefix scheme is connect, is: ", connect)
ngx.exit()
end
## 获取要发送的域名端口信息
local end_start,end_pos = string.find(data," ", 9)
local hostname = string.sub(data,9, end_start - 1)
ngx.log(ngx.ERR, "hostname is: ", hostname)
## 回填到py_upstream变量,以便proxy_pass调用
ngx.var.py_upstream = hostname
## 以正常HTTP方式返回,完成协商
ngx.say("HTTP/1.1 200 OK\r\n")
ngx.flush()
ngx.eof()
}
## 正向代理
proxy_pass $py_upstream;
}
}

如上,就能完成一个http tunnel协议的功能。

Reference

weekly of 20180415

延庆一景

工具技巧

  • Lightweight, Pure-GPU HTML Renderer : 一个纯GPU执行的HTML渲染器,对于游戏类的业务场景会有比较好的支持

  • Is sorted using SIMD instructions : 判断一个数组是否有序的最简单算法,就是遍历数组,依次比较; 但是如果处理器本身支持SIMD之类,会有怎么样的优化算法呢?文章具体说明了如何将上面操作vectorization,以提升判断的速度,结果表明在AVX2的指令集下面性能有100%以上的提升, 对SIMD指令感兴趣的话,可以参看Intrinsics Guide这个指令手册

系统设计

  • NEON is the new black: fast JPEG optimization on ARM server : CloudFlare的技术博客,介绍其对libjpg在ARM平台的优化,主要是讲将在Intel下面优化的SIMD指令在ARM系统上面重写, 总结值得思考: “It is evident that the Qualcomm Centriq is a powerful processor, that definitely provides a good bang for a buck. However, years of Intel leadership in the server and desktop space mean that a lot of software is better optimized for Intel processors.”

  • Salsify : Salsify是斯坦福大学的一个项目,其核心思路是通过对视频编码速率和网络速率的协同控制,来提升real time video的性能和体验,直接感觉意义一般,但是其性能数据体现”reduced delay (at the 95th percentile) by 4.6×, while also improving SSIM by about 60% (2.1 dB)”,先mark,后续有空关注

专题topic

本周关注GPU编程

其他

weekly of 20180408

工具技巧

系统设计

  • 当数据库遇见FPGA:X-DB异构计算如何实现百万级TPS? : 阿里数据库方向的又一个创新,核心问题是, 在基于LSM存储引擎构建的数据库,需要耗费大量的计算量在做SSTable的merge, 这类的compaction计算量大且计算模式相对一致,基于此,其构建了一个传统CPU架构+FPGA的协同计算模式, 对于写密集型的业务场景有着较大效率提升。

  • Lua 5.4 的改进及 Lua 的版本演进 : 先Mark,没有深看,但是非常佩服云风对技术的持续投入和研究~

专题topic

本周关注simd

  • Wikipedia: SIMD : 对SIMD的概念性介绍, 其是一类并行技术的概称”单指令流多数据流”。在具体应用方面,CPU多以SSE(Intel)或者3D Now!(AMD)等提供支持,而GPU则是本身就拥有类似的能力。

  • Introducing SIMD.js : Mozilla发布的SIMD支持的Js Library, 主要是基于CPU的SSE或者NEON提供SIMD能力,希望在games, video and audio manipulation, scientific simulations提升其相关能力。

  • A practical guide to SSE SIMD with C++ : 关于SSE SIMD的实践教程,感觉有点冗长,另外也可以参看Practical SIMD Programming(pdf)

关于TOR)的一些文章

其他