首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >手动实现mkstemp

手动实现mkstemp
EN

Stack Overflow用户
提问于 2013-08-03 14:14:09
回答 2查看 824关注 0票数 2

好吧,在花了好长时间开发一个准备好测试的脚本之后,我现在了解到目标环境没有mkstemp (我愚蠢地相信每个unix-y操作系统都有),它似乎也没有任何其他常见的临时文件实用程序。如果有任何其他广泛可用的临时文件命令,请告诉我,但我不认为我有任何使用。

因此,这意味着我需要自己实现一种形式的mkstemp。现在最简单的方法是像tmp="/tmp/tmp.$$.$RANDOM"这样的东西,虽然这样做并不能保证文件名之间不会发生冲突,所以我需要为此进行测试,但是问题是,在对文件进行测试和创建文件之间,文件可能会意外地被创建,所以它也可能不是一个合适的方法,至少它本身是这样的。

在过去,我必须自己实现一个等价于lockfile的文件,我可以使用一个临时文件移动到位置,使用mv作为一个欺骗(如果它返回一个错误,那么锁已经存在)。我倾向于认为,如果文件已经存在,我可能可以使用一些操作来执行类似的操作,但我不知道最好的方法是什么。

我知道使用/tmp/tmp.$$.$RANDOM不太可能导致冲突,但如果可以的话,我想要正确地实现这一点,因为脚本需要创建相当多的临时文件,然后移到适当的位置,以后我可能需要在其他脚本中做同样的事情,所以正确地这样做是很好的!

编辑:我刚刚意识到,我指的是mktemp everywhere,而不是mkstemp,这是我真正想要复制的(在这里,文件是为您安全创建的)。我想我已经纠正了错误的说法,请原谅我的困惑!

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2013-08-03 16:44:43

通常,创建临时目录的命令行工具称为mktemp,而不是mkstemp。我不确定在所有平台上使用是否安全。如果不是,您可以尝试使用严格的umask创建一个目录,并在该目录已经存在时失败。

代码语言:javascript
复制
mkdtemp() {
    old_mask=$(umask)
    umask 077

    name="/tmp/tmp.$$.$RANDOM"
    mkdir "$name" && echo "$name"
    retval=$?

    umask $old_mask

    return $retval
}

用法:

代码语言:javascript
复制
tempdir=$(mkdtemp) || report_failure

因为这将尝试创建目录(一个原子操作),而不是检查它是否存在并在它生成的名称被接受时失败,所以这个操作是安全的。不过,它很容易受到拒绝服务攻击,攻击者创建许多临时目录就是为了让上面的函数失败。

票数 2
EN

Stack Overflow用户

发布于 2013-08-03 18:02:50

使用@larsman的回答,我想我可能已经找到了自己的答案之一。我不使用mkdir,而是在一个已知的文件上使用cp,特别是/dev/null,它有效地创建了一个空文件,但应该这样做。

对于那些感兴趣的人,以下是代码的简化版本(请原谅任何输入):

代码语言:javascript
复制
mkstemp() {
    umask_old=$(umask)
    umask 077

    name="/tmp/tmp.$$.$RANDOM"
    cp -n /dev/null "$name" 2> /dev/null && echo "$name"
    retval=$?

    umask "$umask_old"
    return "$retval"
}

我已经将上面的内容简化为与larsmans的匹配,因为我的实际解决方案将循环到创建文件或达到尝试限制为止,我使用的行为更接近于mkstemp实际选择名称的方式(使用模板和尾随X),但我认为上面显示了我正在做的事情,它似乎完全符合我的要求!

因此,谢谢拉斯曼,您的解决方案是mkdtemp的一个很好的替身,上面的方法应该和mkstemp的备用方案一样。我可能会将此标记为答案,但我将保留一段时间,以防有人注意到代码有任何问题。

编辑:不幸的是,此方法需要一个带有不受广泛支持的cp标志的-n版本(不要覆盖),但如果目标文件存在但为空,即使这样也不一定有效,因为cp将认为它已经是具有0状态的有效副本和退出。因此,mkdir可能仍然是更好的选择。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/18033736

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档