1/*
2 * Copyright (c) 2022 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 *     http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16#include <dirent.h>
17#include <fcntl.h>
18#include <stdio.h>
19#include <string.h>
20#include <unistd.h>
21#include "test.h"
22
23/**
24 * @tc.name      : symlinkat_0100
25 * @tc.desc      : Create a symbolic link to the specified file
26 * @tc.level     : Level 0
27 */
28void symlinkat_0100(void)
29{
30    char buffer[BUFSIZ];
31    char *path_name = "/data";
32    char *file_name = "/data/symlinkat.txt";
33    char *symlink_name = "mysymlinkat";
34    ssize_t sz;
35    DIR *dp;
36    int fdd, fdf;
37
38    fdf = creat(file_name, O_RDWR | O_CREAT);
39    if (fdf == -1) {
40        t_error("%s creat failed", __func__);
41    }
42
43    dp = opendir(path_name);
44    if (dp == NULL) {
45        t_error("%s opendir failed", __func__);
46        return;
47    }
48
49    fdd = dirfd(dp);
50    if (fdd < 0) {
51        t_error("%s dirfd failed", __func__);
52        return;
53    }
54
55    if (symlinkat(file_name, fdd, symlink_name) < 0) {
56        t_error("%s symlinkat failed", __func__);
57        return;
58    }
59
60    memset(buffer, 0, sizeof(buffer));
61    sz = readlinkat(fdd, symlink_name, buffer, sizeof(buffer));
62    if (sz < 0) {
63        t_error("%s readlinkat failed", __func__);
64        return;
65    }
66
67    if (strcmp(buffer, file_name)) {
68        t_error("%s buffer is %s, not %s", __func__, buffer, file_name);
69    }
70
71    unlinkat(fdd, symlink_name, 0);
72    unlink(file_name);
73}
74
75/**
76 * @tc.name      : symlinkat_0200
77 * @tc.desc      : The file pointed to by the parameter existing does not exist
78 * @tc.level     : Level 1
79 */
80void symlinkat_0200(void)
81{
82    char buffer[BUFSIZ];
83    char *path_name = "/data";
84    char *file_name = "/data/symlinkat.txt";
85    char *symlink_name = "mysymlinkat";
86    ssize_t sz;
87    DIR *dp;
88    int fd;
89
90    dp = opendir(path_name);
91    if (dp == NULL) {
92        t_error("%s opendir failed", __func__);
93        return;
94    }
95
96    fd = dirfd(dp);
97    if (fd < 0) {
98        t_error("%s dirfd failed", __func__);
99        return;
100    }
101
102    if (symlinkat(file_name, fd, symlink_name) < 0) {
103        t_error("%s symlinkat failed", __func__);
104        return;
105    }
106
107    unlinkat(fd, symlink_name, 0);
108}
109
110int main(int argc, char *argv[])
111{
112    symlinkat_0100();
113    symlinkat_0200();
114    return t_status;
115}