Cocoa Oikawa

多用户 Docker 环境下 PyPi 源按需加速

这一篇算是接在上一篇Build a super fast on demand local PyPi mirror的后面吧~

这里会以 docker-compose 的方式为例子,详细写一下~不使用docker-compose的话,则也仅仅需要手动指定 pypicache 与需要这个服务的 container 到同一个 docker 网络中,这样就可以不用去找 pypicache 的 IP 地址,对最终用户透明化,不用增加额外的 pip 安装参数,即可轻松享受本地高速缓存,特别是对于大一点的文件效果更明显~

jupyterhub-docker
jupyterhub-docker

继续阅读多用户 Docker 环境下 PyPi 源按需加速

Build a super fast on demand local PyPi mirror

  • 当公司/局域网里有多人都使用 Python 开发,并且几乎都会用到 pip 来部署环境时,虽然已经有各种镜像源了,但是下载仍受限于与外网的宽带速度,并且同样的包可能被多人下载了多次,在包较大时,重复花的时间并不值
  • 当你使用 Docker 来构建不同的 Python 应用/环境时,在测试 Dockerfile 时可能需要不断的删掉之前 build 的版本,从头开始 build 时,pip 下载与上面面临同样的问题——重复消耗不必要的时间

其一解决方案是公司/局域网内部搞一个 PyPi 的镜像源,实际上维护一个完整的镜像源相当麻烦,占用的储存空间太大,在公司/局域网的情况下,大家开发的东西、使用的技术栈相对比较固定,这就导致完整的镜像源里会有很多包其实几乎没人用。

其二的解决方案可以是预先构建好一个或多个 Docker 镜像,其中包含大家都会用到的包,剩余的一些包则在使用时才被少数需要的人安装。这种方案的缺点则是目前 Docker 服务 + 多用户方案在重启之后会丢掉已经配置过的环境,重启之后依旧需要从镜像源下载包。

那么这里相对一劳永逸的方案则是搭建一个本地的按需下载的 PyPi 镜像源,其原理则是在镜像源与公司/局域网内增加了一个高速缓存,并且由于 PyPi 已经提交分发的whl或者tar.gz是不会变的,因此不用顾虑缓存时间的设置。

最后就像这样~ 182KB/s VS. 36.4MB/s
(cache server为千兆有线链接,MacBook为802.11 AC,测试时链接速度585Mbps)

It's apparently super fast after being cached!
It's apparently super fast after being cached!

继续阅读Build a super fast on demand local PyPi mirror

A brief tutorial on setup an AI lab server for a small team

这个是在之前导师的实验室积累的一些东西,使用场景的话,是适用于2-8人左右的小团队吧,当时有两台机器,一台是放在学校机房的服务器,CPU没注意是什么,印象中是64G内存,4块P20,貌似24G显存?;另一台机器则放在办公室,主要配置的话,一颗AMD Ryzen 2700X,64G内存,再附加两块1080ti 11G,经费肯定是还做不到一人分一块GPU,部分模型的大小也不需要完全独占一块GPU。但是构建一个小型团队使用的AI Lab服务器是没问题了。

当时搭建的AI Lab服务器的主要架构如下

AI Lab Platform Architecture
AI Lab Platform Architecture

系统方面选择了Ubuntu 18.04 LTS,简单方便,毕竟是做AI不是做OS,没有任何必要引入其他方面复杂的操作。然后在这之上则是系统层面的GPU驱动,当时对应的版本为396.26,目前已经有400版本号的驱动了。接下来就是与docker对接的nvidia的runc,由这个runc去给docker内的GPU提供支持。随后当时则是使用了支持多用户的JupyterHub,当然也可以通过分配多个账号解决,这一部分和之后的部分解决方案就很多了。

继续阅读A brief tutorial on setup an AI lab server for a small team

SIGGRAPH 2018 「Semantic Soft Segmentation」复现笔记

santa
santa

SIGGRAPH 2018这篇论文主要分为两大部分,第一部分是 DeepLab v2+ResNet101 训练出来用于获取输入图像的 high-level feature 网络,对于输入的 $I = (h, w, 3)$ 图像,为每一个像素点生成一个 128 维的特征向量,因此该网络的输出是 $F = (h, w, 128)$

接下来,使用 $F$ 和 $I$ 进行引导滤波,$F_{filtered} = imguidedfilter(F, I, 10, 0.01)$,在引导滤波这个地方,OpenCV中的 cv2.ximgproc.guided_filter 与原作者使用的 matlab 中实现的 imguidedfilter 有不小区别,于是我对着 matlab 中 imguidedfilter 的实现重写了一下 OpenCV 版的,bluecocoa/imguidedfilter-opencv

在计算完了 $F_{filtered}$ 之后,利用 PCA 将它压缩到 3 维,$F_{PCA} = PCA(F_{filtered}, 3)$,如下图。

santa PCA
santa PCA

继续阅读SIGGRAPH 2018 「Semantic Soft Segmentation」复现笔记

「Single Image Haze Removal Using Dark Channel Prior」Python Implementation with OpenCV

Haze Removed via Dark Channel Prior
Haze Removed via Dark Channel Prior

A Brief Review


Single Image Haze Removal Using Dark Channel Prior」是 2009 年 CVPR 最佳论文,何凯明博士在这篇论文中提出了暗通道先验的图像去雾算法。

那么暗通道先验是什么呢?这种方法是基于这样的一个观察:

It is based on a key observation most local patches in haze-free outdoor images contain some pixels which have very low intensities in at least one color channel.

简单来说就是对绝大多数没有雾的图像来说,它们的一些局部区域的像素中,某些像素至少有一个颜色通道的值很低。或者对应于原文的「low intensities」,即光强度很低。

我们需要对图像去雾的原因主要是图像中的雾会给很多算法带来麻烦,比如物体识别,特征提取等,它们都默认输入的图像是清晰的,没有雾的。或者不考虑算法,对于在野外或者无人机上的监视摄像头,遇到有雾的场景也是经常的事,即使是人工监视也是需要去雾的。

顺便一提,利用暗通道先验的算法去雾,还可以得到不错的景深图。

Last, the haze removal can produce depth information and benefit many vision algorithms and advanced image editing. Haze or fog can be a useful depth clue for scene understanding. The bad haze image can be put to good use.

在有雾的图像中,一个广泛使用的成像数学模型如下

\begin{equation}
    \mathbf{I}(\mathbf{x})=\mathbf{J}(\mathbf{x})t(\mathbf{x})+\mathbf{A}(1-t(\mathbf{x}))\tag{1}
\end{equation}

我们可以简单的将$\mathbf{x}$理解为图像中的某一个位置,那么,$\mathbf{I}(\mathbf{x})$则是我们最终观察到的有雾的图像在该点的强度;$\mathbf{J}(\mathbf{x})$是在没有雾的情况下,该点应有的强度;$t(\mathbf{x})$是该点的透射率(the medium transmission describing the portion of the light that is not scat- tered and reaches the camera);最后,$\mathbf{A}$是全局大气光强(global atmospheric light)。

图像去雾的目标就是从一张有雾的图像$\mathbf{I}(\mathbf{x})$中,恢复出没有雾的图像$\mathbf{J}(\mathbf{x})$,透射率$t(\mathbf{x})$以及$\mathbf{A}$,全局大气光强(global atmospheric light)。

其中,我们又把$\mathbf{J}(\mathbf{x})t(\mathbf{x})$的结果叫做「直接衰减,direct attenuation」,这个应该比较好理解,就是原始位置反射的光,经过介质(如雾、空气中的其他颗粒)时发生的衰减。然后我们又把$\mathbf{A}(1-t(\mathbf{x}))$叫做Airlight,也就是(先前经过介质时的)散射光导致的色偏。

airlight-and-direct-attenuation

继续阅读「Single Image Haze Removal Using Dark Channel Prior」Python Implementation with OpenCV

「Philosopher」与「Sophist」

前言w~

其实这篇文章是因为我会写一写在阅读古希腊谐剧《鸟》的笔记和一些想法,也算是这个系列的开端吧(但是可能会花上很长的时间来完成它)。其实这个分类「读书人的事」,仅仅是捏他某站点的「稚嫩的魔法师」的书籍推荐系列的视频名字。我读到的、听到的这些仅仅是表面,所以这个分类大概也算是半自嘲或者对自己以后的暗示吧,希望也许哪天真的可以做到「读万卷书,行万里路」吧。

正文~


既然要说古希腊的事,那么避不开的一个话题就是「哲学」。「哲学」这个词在古希腊和在今日的意味是不相同的,我们今日说到「哲学」大概会想到的是在哲学院的那些形而上学的东西。或者说如果哪天你跟家里说,

「木头」是可燃的。我们可以捡回一根木头点燃烧掉它,甚至烧掉地球上所有的木头。但是我们却点不燃那个哲学意义上的「木头」。

家里人的第一反应肯定是“原来你是去读哲学系的啊”(褒义的说w)。

但是在古希腊,「哲学」并不是今日认为的形而上的东西,而是自然科学,比如物理呀、数学呀、天文等等,这些被叫做「哲学」。

所以这里就先来说说「Philosopher」与「Sophist」的事/

继续阅读「Philosopher」与「Sophist」

Monitoring Ivar Changes in Objective-C

As we've mentioned in the last post, Protection against Message Forward in Objective-C, there're at least two tools for tracing the calling sequence of the methods,

However, they just cannot handle it in the scene below,

@interface ProtectedClass : NSObject {
@public
    NSString * _password;
}
@property (nonatomic, getter=password, setter=setPassword:) NSString * password;
@end
/// ...omited...
    ProtectedClass * obj = [[ProtectedClass alloc] init];
    obj->_password = @"喵咕咪~"; // directly access, undectectable in BigBang or ANYMethodLog
    [obj setPassword:@"喵"]; // BigBang or ANYMethodLog dectectable
/// ...omited...

Because it's not necessarily to call getter or setter in Objective-C when access or change an ivar. Since Objective-C is just a superset of C, so the object (or instance) in Objective-C acts pretty much like the struct in C. You can directly access its member if you have the memory address. Let's check out what happens when compiling.

Here is our code, written in Objective-C, and it's probably quite often to be seen in your projects.

Objective-C code
Objective-C code

继续阅读Monitoring Ivar Changes in Objective-C

Protection against Message Forward in Objective-C

A Brief Review


Runtime is one of the powerful features of Objective-C, it provides us the ability to add/replace a method of some class, retrieve/set the implementation of a specified method, and even add a class in runtime.

However, just like the sunlight shines not only on the good guys, but also on the bad ones. There are some tools in iOS Jailbreak community which take the advantage of Objective-C's runtime feature, to be specific, the ability of message forward. Within this feature, they can log the calling sequence of the methods in the application for further exploitation. And it's not that hard to inject such tools into your application, since there are many ways such as DYLD_INSERT_LIBRARIES or modifying the MachO load commands, and they got some sets of tools like iOSOpenDev, and the new replacement of iOSOpenDev, MonkeyDev by @AloneMonkey.

And there're at least 2 tools which can log the calling sequence of the methods,

Hooked via forwardInvocation
Hooked via forwardInvocation

继续阅读Protection against Message Forward in Objective-C

すごーい!たーのしー!