Skip to content

对 Cygwin 的支持需要让用户主动声明 #140

Closed as not planned
Closed as not planned

Description

@ccmywish

在 #65 和 #133 中,我们都涉及到了 Cygwin 和 MSYS2 的问题。

第一次错误的认识

在第一次尝试解决这个问题的时候,我花了一下午,最终确认是在 Cygwin 上的 /usr/bin/curl 的问题。即,我认为三种不同环境下编译的 curl.exe (Cygwin 下、MSYS2下、原生Windows下)的行为不一致,所以最终归咎于上游。


新的认识

然而今天经过再次研究,发现这一问题的根源,并不是上述编译 curl 的环境或者编译配置等问题。而是整个 Cygwin 环境的问题:Cygwin 无法识别 nul 文件。而 MSYS2 修正了这个问题。

所以判断 Cygwin 环境成为了我们的一个主要目标。


检测Cygwin的方案

上一次,我们是使用 cygcheck.exe 这一命令来检测的,这一命令在 Cygwin 和 MSYS2 中都存在。@Yangmoooo 指出用户很有可能把 Git Bash 的路径加入 Windows 原生环境变量中,导致上述检测方案失效。

接着寻求其它方案:Cygwin 环境并没有暴露出任何环境变量,唯一的 CYG_SYS_BASHRC 也没有被 export 出来。通过环境变量的检测手段失败了,接着我想要通过路径来检测,然而 Windows 上的 access() 以及原生的 GetFileAttribute() 都无法检测到 /usr 这种目录。遂这种方案也失效。


鸡蛋问题

我们可以通过调用 which, test 等命令检测,但是在原生 Windows 上这个命令不存在,因而需要 >nul 2>nul,此时在 Cygwin 环境中,又会生成 nul 文件(即使内容为空,也会产生)。我们发现,我们又回去了,陷入了鸡生蛋蛋生鸡的问题。

所以我提出这个方案:仍然基于第一次的修改,但现在额外让用户付出一个小的代价:让 Cygwin 用户主动暴露一个 export ON_CYGWIN=1 供我们检测,检测到后,再利用我们现有的实现去迂回地测速。即,修改这一条件:https://github.com/RubyMetric/chsrc/blob/main/src/framework/core.c#L498

#if  XY_On_Windows
  // if (0==system ("cygcheck --version >nul 2>nul"))
  if (getenv ("ON_CYGWIN"))
    {
      on_cygwin = true;
      os_devnull = "/tmp/chsrc-measure-downloaded";
    }
#endif

Activity

  1. self-assigned this
    on Dec 8, 2024
  2. added this to the v0.2.0 milestone on Dec 8, 2024
  3. ccmywish commented on Dec 8, 2024

    @ccmywish
    ContributorAuthor
    1. 相关用户:@anaer @xyx1926885268

    2. 方案协助审核:@happy-game @Yangmoooo

  4. Yangmoooo commented on Dec 8, 2024

    @Yangmoooo
    Contributor

    @ccmywish 感谢您详尽的回复。事实上,我在尝试了几种方式后,初步得出了两个解决方案:

    1. 根据 uname 命令可以正确区分 Windows、MSYS2 和 Cygwin 环境,以此改进之前的判断逻辑

    2. 将 Windows 平台上的测速工具统一指定为 C:\Windows\System32\curl.exe

    根据我的测试,这两种方案都能够解决现有的环境判断和 nul 文件的问题,但我更倾向于方案二,原因如下:

    1. 这三种环境本质上都属于 Windows 平台,都存在 C:\Windows\System32\curl.exe,且对于原生 Windows 程序的处理相同

    2. 统一的工具能够简化未来的开发工作

    3. 统一使用 Windows 原生的 curl.exe 可以去除之前不必要的环境判断补丁,代码更加清晰

    如果需要,我会在晚些时候提交 PR

  5. ccmywish commented on Dec 8, 2024

    @ccmywish
    ContributorAuthor

    @Yangmoooo 感谢你持续关注这个问题,并提出自己的方案。

    1. 用 uname 还是避免不了鸡蛋问题。因为 Windows 里没有 uname,用 system() 去调用时,只能又去添加 >nul 2>nul

      或者说,你的方案里不需要加 >nul 2>nul 吗?

    2. C:\Windows\System32\curl.exe 在 Windows 7 中是没有的

    3. 统一指定为 C:\Windows\System32\curl.exe

      刚才测试了一下,在 MSYS2 中成功,但在 Cygwin 中无法找到该路径

  6. Yangmoooo commented on Dec 8, 2024

    @Yangmoooo
    Contributor

    我前面说的比较笼统,对于这三个问题:

    1. 我是先通过 MSYSTEM 环境变量判断 MSYS2,然后用 uname 2>nul 区分 Windows 和 Cygwin,因为 Cygwin 正好无法识别 nul 文件

    2. Windows 7 的兼容性我确实没有考虑到 😂,但是我看到较新版本的 MSYS2 和 Cygwin 也不再支持 Windows 7,那么可能本来也没有 curl 命令

    3. 在 Cygwin 的终端中确实不能直接调用 Windows 的 curl.exe,但在 C 程序中的 popen 函数(即 chsrc 里的 xy_run)是可以的

  7. happy-game commented on Dec 8, 2024

    @happy-game
    Collaborator

    也许可以使用libcurl进行测速, 并最终静态编译发布, 这样就不用再考虑curl的问题了, 也可以简化用户的操作(因为有些发行版甚至不会默认安装curl).

    但也存在几个问题:

    1. 对现有代码需要进行较大的修改
    2. 最终发布的二进制文件体积可能会更大
    3. 开发者需要额外安装libcurl再编译
  8. ccmywish commented on Dec 9, 2024

    @ccmywish
    ContributorAuthor

    已修复,见 #144

    感谢各位 ❤️ @anaer @xyx1926885268 @happy-game @Yangmoooo

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

WindowsWindows相关计划计划 Plan讨论讨论 Discussion

Type

No type

Projects

No projects

    Milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions