简体   繁体   English

了解文件截断

[英]Understanding File Truncation

Quoting from Advanced Programming in the UNIX Environnement (page 505), Section 13.6: 引用Advanced Programming in the UNIX Environnement (第505页),第13.6节:

We need to truncate the file, because the previous instance of the daemon might have had a process ID larger than ours, with a larger string length. 我们需要截断该文件,因为守护进程的前一个实例可能有一个比我们大的进程ID,并且字符串长度更长。 For examples , if the previous instance of the daemon was process ID 12345, and the new instance is process ID 9999, when we write the process ID to the file, we will be left with 99995 in the file. 例如,如果守护进程的前一个实例是进程ID 12345,而新实例是进程ID 9999,那么当我们将进程ID写入文件时,我们将在文件中留下99995。 Truncating the file prevents data from the previous daemon appearing as if it applies to the current daemon. 截断文件会阻止前一个守护程序中的数据显示为应用于当前守护程序。

This comment was made on this function: 这个评论是在这个功能上做出的:

already_running(void)
{
    int fd;
    char buf[16];
    fd = open(LOCKFILE, O_RDWR|O_CREAT, LOCKMODE);
    if (fd < 0) {
        syslog(LOG_ERR, "can't open %s: %s", LOCKFILE, strerror(errno));
        exit(1);
    }
    if (lockfile(fd) < 0) {
        if (errno == EACCES || errno == EAGAIN) {
            close(fd);
            return(1);
        }
        syslog(LOG_ERR, "can't lock %s: %s", LOCKFILE, strerror(errno));
        exit(1);
    }
    ftruncate(fd, 0);
    sprintf(buf, "%ld", (long)getpid()); 
    write(fd, buf, strlen(buf)+1);
    return 0;
}

I don't understand how is this behavior possible, and how file truncation prevent that behavior from happening. 我不明白这种行为是如何可能的,以及文件截断如何防止这种行为发生。 Could somebody explain this? 有人可以解释一下吗?

Thanks for answering! 谢谢回答!

In the above example, the file is initially 5 bytes long. 在上面的示例中,文件最初为5个字节。 When you open it for writing, and write the string "9999" to it without truncating, it will just overwrite the first 4 bytes, and leave the 5th byte in place. 当你打开它进行写入,并在不截断的情况下将字符串“9999”写入其中时,它将覆盖前4个字节,并保留第5个字节。 Hence the file will read "99995". 因此该文件将显示为“99995”。 Truncating sets the file length to 0, effectively erasing the previous content. 截断将文件长度设置为0,从而有效地删除先前的内容。

Hellmar has already provided the answer to your question -- but in the interest of shortening the code (who doesn't like code golf?), you could simplify the open call to: Hellmar已经提供了你的问题的答案 - 但为了缩短代码(谁不喜欢代码高尔夫?),你可以简化公开调用:

already_running(void)
{
    int fd;
    char buf[16];
    fd = open(LOCKFILE, O_RDWR|O_CREAT|O_TRUNC, LOCKMODE);
    ...

The addition of O_TRUNC to the flags will cause the file to be truncated. 向标志添加O_TRUNC将导致文件被截断。 http://linux.die.net/man/2/open http://linux.die.net/man/2/open

If the file already exists and is a regular file and the open mode allows writing (ie, is O_RDWR or O_WRONLY) it will be truncated to length 0. 如果文件已经存在且是常规文件且开放模式允许写入(即,是O_RDWR或O_WRONLY),则它将被截断为长度0。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM