完全用 AI 开发了一个应用:FakeEsptool

去年的时候,感觉自己对乐鑫的芯片加密细节并不是很熟悉。特别是像针对每个设备不同的预设工厂 NVS 加密数据如何烧录,就没有一个清晰的思路。所以,就想着,我能做一个程序来欺骗 esptool.py 让它以为我是芯片,就可以分析出具体的细节。想法虽好,但实际上是一个鸡生蛋、蛋生鸡的问题。也得通过真实设备的逆向才能完善这个程序设计。

上个月的时候,无意中薅到 Mimo 的一个月 Pro 套餐,简单测试(分析历史项目代码)后,就开工了。

一开始的尝试是一个失败的或者说失控的 AI 开发。Agents 根本就无法理解完整的需求和细节。所以,先分拆需求。完成一个简单的版本,只实现一个纯 C 的 Win32 GUI 串口通讯框架程序 SerialEcho 用于后期开发。基本上实现了 Win32 串口框架和协议日志 Dump 界面。

然后,再开始真正的开发。采用的方式是文档先行。先用需求文档设计好界面功能,再用协议文档约定好实现细节。本来协议是准备从官方文档扩展而来。但实际上 esptool 官方协议文档完全不足以覆盖 Fake 开发的细节内容。于是,采用逆向烧录器端的代码实现,用 AI 反向推理协议和实现细节,再辅以逻辑分析仪对真实协议数据抓包来校正。

前期的程序框架开发和测试避免了后期开发陷入的复杂性问题。只要能把问题抽象到基本框架代码上重现,就不需要在后面负责架构上去定位问题和解决。

当然,因为 FakeEsptool 本身就是为了逆向而开发的工具,天然的设计了足够强壮的协议通讯日志系统。有了逻辑分析仪抓包的数据,AI 可以很轻松的找到问题所在,人工复现这一流程,通常是很痛苦的体力活。还需要足够的细心。。。

花了大半个月时间和上百亿 Credits 后,第一个版本终于完成了。这也只是一个不涉及到加密的基础模拟版本,至少可以欺骗 esptool.py 和 idf.py flash 了。

而原本项目立项的初衷,还是需要有足够的芯片来逆向加密烧录的通讯。

ESP32软件映射一个IO的输出到另一个IO的输入

ESP32 所有处理器都带有 IO MUX 功能,也就是 IO 可以随意绑定绝大部分内部功能和信号。所以就可以用未使用的内部信号绑定两个 IO,让其中一个 IO 的输出直接输出到另一个 IO 当作输入。这样,无需物理连接,就可以直接用来测试相关程序。

绑定一个输出 IO 到输入信号:

esp_rom_gpio_connect_in_signal(gpio_a, SIGNAL_IDX, false);

这里的 SIGNAL_IDX 需要在芯片对应的 soc/gpio_sig_map.h 文件中选择 SIG_IN_FUNC 开头的索引值,比如 ESP32 的 SIG_IN_FUNC228_IDX。不同芯片的可用索引值不一样。

然后将这个信号输出到另一个 IO:

esp_rom_gpio_connect_out_signal(gpio_b, SIGNAL_IDX, false, false);

输入和输出都有参数可以选择如何反转 IO 信号。

如果不需要映射,恢复输出信号的 IO 映射:

esp_rom_gpio_connect_out_signal(gpio_b, SIG_GPIO_OUT_IDX, false, false);

SIG_GPIO_OUT_IDX 的值通常是 0x100。但其实不同的驱动,IO 也会绑定到其他的信号上,所以需要参阅相关驱动代码来恢复映射设置。

重装 scoop

scoop 是绿色安装,也就是可以直接备份恢复,安装的 app 也能通过 scoop reset app 来恢复开始菜单的快捷方式。但是对于 scoop 本身就没有办法。使用官方安装脚本只会提示 scoop 已安装(很尴尬。。)。

除了官方 issue 推荐的删除 scoop 再安装的傻办法(会清除所有已安装的 app)外,还可以将现有的 scoop 改名,再安装 scoop,之后再将新安装的 scoop 目录直接删除,最后将旧有的 scoop 目录名称还原。😀

Gitlab CI 多个作业编译不同配置的 ESP-IDF 固件

首先需要将不同的 kconfig 配置放入不同的文件,比如 sdkconfig.foo。对于相同配置,还是放入 sdkconfig.defaults

比如,sdkconfig.foosdkconfig.bar 的文件内容分别如下:

# sdkconfig.foo
CONFIG_FOOBAR=foo
# sdkconfig.bar
CONFIG_FOOBAR=bar

对应的 .gitlab-ci.yml 如下:

image: espressif/idf

stages:
  - build

.template: &template
  stage: build
  variables:
    GIT_SUBMODULE_STRATEGY: recursive
  script:
    - idf.py -DSDKCONFIG_DEFAULTS="sdkconfig.defaults;sdkconfig.$CI_JOB_NAME" build
  artifacts:
    expire_in: 1 day
    name: "$CI_JOB_NAME-$CI_COMMIT_BRANCH-$CI_COMMIT_SHORT_SHA"
    paths: 
      - build/*.bin
      - build/bootloader/*.bin
      - build/partition_table/*.bin

foo:
  <<: *template

bar:
  <<: *template

这样,每次提交都会针对 CONFIG_FOOBAR=fooCONFIG_FOOBAR=bar 构建两个固件了。

使用 GitLab Auto DevOps 在 Kubernetes 上部署 Yii2 应用

首先,感谢 Guillaume Simon 的 Deploying Symfony test applications on Kubernetes with GitLab Auto DevOps, k3s and Let’s Encrypt – A 30m guide 一文给予我最大的帮助,使得本文能够完成。

其次,这里只涉及到部署。也就是只包含下列内容:

在未来可能会支持:

也希望有人在这方面为此项目创建拉取请求

最后,相信你看得懂上面的文字说明,并为此而来。我们继续~

(更多…)

小宝宝两个月了

真的是好辛苦。

从六月份宝宝妈妈去医院不小心遭遇流感开始,整个日子都乱套了。来回奔波,连平常不用的车都跑了三四千公里里程。等到宝宝出生,除开在医院的三天,大人小孩就没睡过完整的一晚上觉。

WiFi 配置 IPv6 指南

根据工信部的要求,2018 是 IPv6 大力推进部署的一年。截止到年底 12 月份,对于普通用户来说,三大运营商对 IPv6 的支持已经从宽带上网落实到手机移动网络的双栈支持。不管是 Android 用户还是 iOS 用户(12.1.1 已提供联通描述文件),都能直接使用到原生的 IPv6。

不过,因为老旧路由器的限制,即使光纤宽带上网早早就已支持 IPv6,但绝大多数 WiFi 并不支持 IPv6。

具体来说,家庭 WiFi 要支持 IPv6 需要满足三个条件:

  1. 运营商支持 IPv6(三大运营商在大多数城市都已支持)
  2. 光猫支持 IPv6(最近两年运营商赠送的光猫均支持)
  3. WiFi 路由器支持 IPv6(很遗憾,国内主流路由器很少支持)

所以,配置 WiFi 的 IPv6 首先要选择支持 IPv6 的路由器。当然,还有一种选择就是,路由器可以刷第三方固件。大多数第三方固件目前都提供有 IPv6 支持。

另外,运营商提供的光猫现在也提供有 WiFi 和路由功能,也能直接开启 IPv6 支持。

对于中国电信的光猫,建议使用 telecomadmin 账号和 nE7jA%5m 密码以超级管理员登录。然后在“状态总览”的“业务信息”下“上网业务”查看是否有 IPv4 和 IPv6 两个连接。使用路由器的用户,将看到连接方式为“桥接(电脑拨号)”。

如果没有看到 IPv6,请转到“网络”的“网络设置”页面。找到“网络连接”的“连接名称”类似于“3_INTERNET_B_VID_41”选项,其“封装方式”为“PPPoE”,“业务类型”为“上网”,“连接方式”为“桥接”(如果是路由表示开启了光猫的路由功能)。请将其“IP 模式”修改为“IPv4 & IPv6”即可开启双栈支持。

对于路由器,比如潘多拉固件。在 WAN 口 IPv6 设置页面:“IPv6 连接类型”选择“Native DHCPv6”,“获取 IPv6 外网地址”选择“Stateless: RA”,“启用 LAN DHCPv6 服务器”选择“Stateless (*)”;然后开启“自动获取 IPv6 DNS”、“通过 DHCPv6 获取内网 IPv6 地址”、“启用 LAN 路由器通告”。

Ubuntu LVM 增加新硬盘

办公室放着一台测试机,想着做备份用,但只有一块 500G 的硬盘,不太够。所以得增加硬盘。

Ubuntu 12.04 LTS 就已经支持 LVM 安装,14.04 LTS 默认会选择 LVM 了。而且对于 500G 硬盘,也会默认使用 GPT 分区。

(更多…)