V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
V2EX  ›  geelaw  ›  全部回复第 4 页 / 共 177 页
回复总数  3530
1  2  3  4  5  6  7  8  9  10 ... 177  
150 天前
回复了 a2233 创建的主题 发音 大家是如何读 CLI 的?
“老外”不止是说英语的……英语读 see-elleye ,法语读 cé-elle-i ,汉语读 cê-êl-yi 。
@hez2010 #9 现象和规范是两码事,单纯做一个实验就认为 Windows 支持超长变量无异于依赖于 C++ undefined behavior 编程。

应该注意 Win32 环境变量有两个存在的形式:在注册表里存储的系统/用户级变量、在每个进程里存储的进程级变量。

考虑下面的每个实验,每个实验开始之前都不存在名字叫做 verylong 的系统、用户、进程级环境变量。

————

实验 1:在 PowerShell 里运行

[System.Environment]::SetEnvironmentVariable('verylong', '1'*40000, 'User')

然后通过 explorer 打开一个新的 PowerShell ,并在新的 PowerShell 里运行

$env:verylong.Length

在 Windows 10 (build 19045.4651) x64 里得到的结果是 4095 ,这说明 explorer.exe 把 %verylong% 截断为 4095 个字符了。

————

实验 2:在 PowerShell 里运行

[System.Environment]::SetEnvironmentVariable('verylong', '1'*40000, 'User')
$cred = Get-Credential
Start-Process powershell -cred $cred -arg '-Command start powershell'

输入当前用户的用户名和密码,然后等待新的 PowerShell 启动(注意这里需要两次跳转,似乎有不知名的 bug 导致单纯打开一次 PowerShell 无法输入),在新的 PowerShell 里面运行

$env:verylong.Length

得到 40000 ,这说明“什么都不做”似乎是可以自动读取超长环境变量,然而……

————

实验 3:在 PowerShell 里运行

[System.Environment]::SetEnvironmentVariable('verylong', '1'*40000) # 默认的范围是进程

会得到

Exception calling "SetEnvironmentVariable" with "2" argument(s): "Environment
variable name or value is too long."

查阅 PowerShell 的源代码,发现这个异常是从 Win32 API SetEnvironmentVariable https://learn.microsoft.com/en-us/windows/win32/api/winbase/nf-winbase-setenvironmentvariable 来的(而不是 PowerShell 自己检查的),文档明确指出超过 32767 个字符是不支持的,实际调用也会返回 FALSE 并用 GetLastError 指示变量过长。

————

实验 2 、3 表明实际上超过 32767 个字符的环境变量是不支持的,因为用于访问之的 Win32 API 拒绝设置超长变量。至于“什么都不做”的时候可以读到超长环境变量,单纯是 Windows 从注册表读取的时候、通过 GetEnvironmentVariable 返回的时候,忘记验证了。

考虑不变式

LPCTSTR name = T("verylong");
TCHAR value[40001];
DWORD size = 40001;
DWORD actualSize = GetEnvironmentVariable(name, value, size);
BOOL couldSet = SetEnvironmentVariable(name, value);

自然期待单线程环境下 actualSize > 0 && actualSize < size (这表明获取名字是 verylong 的环境变量成功了)蕴涵着 couldSet (这表示可以做无意义且无害的赋值),但这个不变式因为 Windows 的实现很不小心所以不一定成立。

然后,在做了上面的实验之后,我会认为日常使用的时候应该避免变量内容超过 4095 个字符,因为 Windows 最常见的 shell 即 explorer.exe 不支持超长的变量。
@hez2010 #6 我对英语的解读和你的不同,原文

> The maximum size of a user-defined environment variable is 32,767 characters. There is no technical limitation on the size of the environment block. However, there are practical limits depending on the mechanism used to access the block. For example, a batch file cannot set a variable that is longer than the maximum command line length.

说的是

1. 一个环境变量不能超过 32767 个字符。
2. 环境块没有限制。注意每个环境块是多个环境变量赋值的双空结尾字符串,这里说的是可以有任意多个环境变量。
3. 访问环境块的方法会带来其他限制,
4. 比如批处理文件不能设置环境变量的值为超过单行最大字符数长度的字符串。这个数是几千。

待会儿我到电脑附近的时候可以试试。
@hez2010 #3 然而这和文档说的相反,根据

https://learn.microsoft.com/en-us/windows/win32/procthread/environment-variables

环境变量的长度不能超过 32767 个字符。
@FengMubai #1 那个是去掉一些 API 里面路径长度的限制,和环境变量长度是两码事。

这个问题比较无解,因为 PATH 是知名变量,如果希望 PATH 里面有所需要的路径,但需要的路径太多,则必然会超过长度限制。所谓回到 PATH 内,是指进程里面的 PATH 变长,还是用户级别的 PATH 变长,还是系统级别的 PATH 变长?第一种解决方法是时不时从一个干净的根进程重启其他进程;第二种、第三种要找出来是谁(哪个进程)在随意修改环境变量。
代码的书写方向就是代码所用字符的书写方向,如果是 Latin 字母的代码,那就是从左到右。

在 RTL 环境里插入一段 LTR 文字,LTR 文字本身是从左到右书写的,比如

.言语的写书左到右从 is a 文伯拉阿

然而如果 LTR 文字本身需要超过一行,我想应该是每一行都要按 RTL 环境插入 LTR 文字书写,比如

is written from 文伯拉阿
.惯习太不会以所 right to left

最近翻看 Wikipedia 知道的:阿拉伯文本里面书写西阿拉伯数字,是从右到左书写的,但低位在前,所以看起来和中午里的阿拉伯数字是一样的,比如

.3.1415926 字文语伯拉阿些一有里这装假
@drymonfidelia #42 和 Edge 保护不保护隐私没啥关系,觉得幽默是因为通常会假设 MS 会把各种 Google 专有的东西删除或者换成 MS 专有的。

@zhangdp #47 对 Google 有用。
这件事情的幽默之处在于 MS Edge 也给 google.com 高权限。来源是 https://x.com/lcasdev/status/1810753964020773316 但我没有验证
@CRVV #78 你可能没有理解“总”能耗的含义。考虑发送电子邮件给 N 个人,自然期待 N 个人分别需要解密一次。

考虑 N 时间 1 长度的方案,那么每个收件人需要下载长度是 1 的密文,然后用 N 的时间运行解密算法,因此总能耗是 1*N+N*N = Theta(N^2)。

考虑 1 时间 N 长度的朴素方案,每个收件人需要下载的密文长度不是 N ,因为在 1 的解密所需时间内,整个长度是 N 的密文只有常数个位置被访问,因此每个收件人的下载是 1 ,解密时间是 1 ,总能耗是 1*N+1*N = Theta(N)。

两种情况里存储 O(N) 的密文以及在 O(N) 时间内加密所消耗的能量都被 Omega(N) 的下载、解密所吸收。
@CRVV #75 环保的考虑里面是计算了存储和传输数据需要的能量的,请注意“总能耗”的“总”字。

>要获得 “密文长度和收件人数无关” 这个性质,还是需要折腾一些花样进去。

获得这个性质所需要的技巧,我称之为“繁琐但常规的体操”。从技巧评判,这篇文章比较有趣的是环保问题,毕竟证明不可能性比证明可能性困难一些。至于问题本身是否有趣,每个人有不同的想法很正常。

您所谓“科研的玩法”,不可否认科研用作赖以生存的职业会有那种考量,但我的建议是晚一会儿想这个问题是一会儿。
@wy315700 #44 这个图好好玩,不过其实不像。比如,至少这个加密算法是安全的,但这个门上的锁和没有一样(

@barlogscc #46 投了两年才接受,不应该是太弱了吗……?

@chf007 #53 要想多个人解密结果不同,需要泛函加密( functional encryption )。要想解密后的结果可以识别是谁,需要水印、指纹码( fingerprinting code )。不过这两个都不实用。

@insignificance #59 没有。

@iamyourking #54 @justNoBody #70 能够被追踪的不是单个解密结果,而是解密的 *能力*。
@fxyr123456 #74 其实 #11 就是答案了。

更具体一点的话,加密算法有一种特殊的模式,可以禁用 L 中一些人的解密能力。平常加密不禁用任何人。要追踪的时候,用特殊模式,测试禁用前 0, 1, ..., |L| 个人之后 D 解密能力的变化:

1. 禁用前 0 个人(平常)的时候 D 解密能力较强,禁用前 |L| 个人(所有人)的时候 D 的解密能力归零,因此在禁用的途中 D 的解密能力会逐步下降。
2. 如果 D 不蕴涵 i 的私钥,则根据加密算法的安全性,禁用 i 前后 D 的解密能力不能发生变化( D 此时不能知道 i 是否被禁用)。

综合这两点,如果禁用 i 前后 D 的解密能力明显下降,则指认 i 是叛徒。这个框架是 2006 年 [BSW06] 就知道的了。

实际的保障更强一些,用人话来说:如果 D 导致加密给 L 的密文稍微有一点儿不安全( D 不需要“能够完全解密”),那么可以识别 D 中蕴涵 L 里哪个人的私钥。
推荐搜索的关键字是 deniable encryption (可抵赖加密),我印象里最开始大家对它感兴趣是因为它可以用来构造适应性安全的 MPC ,是相当非平凡的问题,这种加密可以用程序混淆构造。

在知乎写过一个简单的科普 https://www.zhihu.com/question/576682585/answer/2933493982
@nealHuang #22 原帖是这个意思。

@sniperboy0829 #23 MPC 不是 blockchain “里面的”,不太理解您在说啥。
我、审稿人认为该问题是新的,早期文献已经考虑或解决这个问题的概率微乎其微。

@jhdxr #38 这个问题和 MPC 可能都不算 remotely related 吧。没有涉及“多个人有秘密且他们想要计算多元函数”的情况。在“追踪”这个步骤里面,是任何一个想要找出叛徒的人都可以通过调用 D 来找到,在“脑内模型”里面 D 就是一个坐在云端的接口,或者(在中心化的版本里)可以想象成一个不理睬 DRM 的 DVD 盗播机器。

@nomagick #28 第 2 、3 、4 个问题的答案是,我在本帖的表述也力求准确:
>某 *些* 人制造了程序……找出……哪 *个* 人的私钥……
考虑的问题本来就涵盖了使用多个私钥建立 D 的情况。
你也可以参考现在版本里:摘要第一段最后一句话、定义 12 、脚注 8 、构造 2 、构造 3 。

关于民科的问题,拜资格主义( credentialism )不好。
@lovelylain #11 朴素做法是这样的。不朴素的话,可以用程序混淆( program obfuscation )压缩密文,当然要保持逐一破坏的功能,最短可以让密文长度和收件人数无关。
174 天前
回复了 ddmasato 创建的主题 Apple ios safari 居然原生不支持暗黑模式?
浏览器支持亮暗主题的意思是它可以告诉网页当前期待的主题是哪一种(从而网页的代码可以作出反应),而不是它可以修改网页。

类比:图形操作系统的意思是它提供 API 创建 GUI ,而不是能把基于文本命令的程序变成 GUI 程序。
第一个问题,我的理解是编译失败,因为 &a 是指向 int[5] 的指针,于是 &a + 1 也是指向 int[5] 的指针,它指向整个数组之后的 past-the-end 位置,然而 p 是指向 int 的指针,这是两个不兼容类型,当然初始化不能成功。至于具体的编译器接受此代码,只能说是不合标准。

编译失败的原因同

typedef int my_array_t[5]; /* 方便看清楚 */
my_array_t a;
my_array_t *q = &a;
my_array_t *r = q + 1;
int *p = r; /* 当然是无稽之谈 */

第二个问题,如果你说的是 unsigned 类型,那么 x != 0 && (x & (x - 1)) == 0 ,如果是 int 类型还需要判断符号。

后面略,这些问题是惟手熟尔。

@basncy #26 C 和 C++ 里面恰好超过最后一个元素位置的指针是有效的,只是不允许解除引用。考虑 int a[5]={}; int *begin = a, *end = a + 5; while (begin != end) printf("%d\n", *begin++); 当然是 OK 的代码。

@w568w #29 a 确实不是数组元素,但是对于指针运算来说,单个对象等同于具有一个元素的数组对象的惟一元素。也就是说 int b; int *begin = &b, end = &b + 1; 是正确的代码。
我的建议是让本人自己想,自己选。
1  2  3  4  5  6  7  8  9  10 ... 177  
关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   2641 人在线   最高记录 6679   ·     Select Language
创意工作者们的社区
World is powered by solitude
VERSION: 3.9.8.5 · 35ms · UTC 07:02 · PVG 15:02 · LAX 23:02 · JFK 02:02
Developed with CodeLauncher
♥ Do have faith in what you're doing.