如何在Linux上将常规文件转换为符号链接

ua4mk5z4  于 2023-10-16  发布在  Linux
关注(0)|答案(3)|浏览(125)

我正在写一个(联合国)归档工具,它的设计方式是首先从归档文件中创建一个常规文件,然后检查特殊属性,并可能决定这个项目是一个符号链接,事实上。

注意:在更多的人误解我想做一个文件的符号链接之前。不,我写的符号链接数据,即。它的路径,进入文件,然后我想告诉文件系统,这是一个符号链接

我一直在OS X上开发这个,在那里可以通过简单地设置其类型和创建者代码将常规文件转换为符号链接。
现在我想让这段代码也能在Linux上运行。所以我喜欢在那里找到类似的方法。
我知道创建符号链接的正常方法是调用symlink()函数,但我想知道是否也有一种方法可以将常规文件更改为符号链接,就像在OSX的BSD系统中一样,这样我就不必重构我的工作代码太多?
有一个lstat(),它返回st_mode最高位的文件类型。现在我想知道是否也有一个类似的setter函数用于这个模式字段。

gwbalxhn

gwbalxhn1#

我不相信在Linux中有一种方法可以像你描述的那样做到这一点。文件系统将符号链接信息存储在inode表中,而不是存储在常规文件中,因此没有直接的方法将文件转换为链接。
如果符号链接的路径存储在文件中,为什么不读出路径,删除文件,并在其位置创建一个符号链接呢?

w8biq8rn

w8biq8rn2#

为了证明我对bmarguiles的回答的评论,

#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <unistd.h>
int main(int argc, char **argv) {
    char *buffer = 0, *name = 0;
    int i;
    for (i = 1; i < argc; i++) {
        struct stat st;
        int fd = open(argv[i], O_RDONLY);
        fstat(fd, &st);
        buffer = realloc(buffer, st.st_size + 1);
        read(fd, buffer, st.st_size);
        close(fd);
        buffer[st.st_size] = '\0';
        name = realloc(name, strlen(argv[i]) + 2);
        sprintf(name, "%s~", argv[i]);
        symlink(buffer, name);
        rename(name, argv[i]);
    }
    free(buffer);
    free(name);
    return 0;
}
$ vi f2s.c
...
$ cc -o f2s f2s.c
$ echo -n / > test
$ ./f2s test
$ ls -l test
lrwxrwxrwx 1 me me 1 Feb 24 23:17 test -> /
$ echo -n / > test2
$ strace ./f2s test2
open("test2", O_RDONLY)                 = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=1, ...}) = 0
read(3, "/", 1)                         = 1
close(3)                                = 0
symlink("/", "test2~")                  = 0
rename("test2~", "test2")               = 0

这只是一个示范;它真的需要更多的错误处理,也许是一个更好的临时文件名。

tyg4sfes

tyg4sfes3#

不你不能把一个变成另一个你必须取消链接来杀死文件,然后创建一个符号链接作为替换。

相关问题