1 /*
2  * Copyright (C) 2024 HiHope Open Source Organization.
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 <cstdio>
17 #include <cstdlib>
18 #include <fcntl.h>
19 #include <string>
20 #include <unistd.h>
21 #include <vector>
22 #include <gtest/gtest.h>
23 #include <sys/stat.h>
24 #include <sys/types.h>
25 #include <sys/xattr.h>
26 #include "securec.h"
27 
28 using namespace testing::ext;
29 using namespace std;
30 
31 static const char *TEST_FILE = "/data/local/tmp/test_file.txt";
32 static const char *TEST_DATA = "Hello, world!";
33 static const size_t TEST_LEN = strlen(TEST_DATA);
34 
35 class LseekApiTest : public testing::Test {
36 public:
37     static void SetUpTestCase();
38     static void TearDownTestCase();
39     void SetUp();
40     void TearDown();
41 private:
42 };
SetUp()43 void LseekApiTest::SetUp()
44 {
45     int fd = open(TEST_FILE, O_WRONLY | O_CREAT, 0644);
46     write(fd, TEST_DATA, TEST_LEN);
47     close(fd);
48 }
TearDown()49 void LseekApiTest::TearDown()
50 {
51     (void)remove(TEST_FILE);
52 }
SetUpTestCase()53 void LseekApiTest::SetUpTestCase()
54 {
55 }
TearDownTestCase()56 void LseekApiTest::TearDownTestCase()
57 {
58 }
59 
60 /*
61  * @tc.number : SUB_KERNEL_SYSCALL_LSEEK_0100
62  * @tc.name   : LseekSetOffsetTestSuccess_0001
63  * @tc.desc   : lseek set the offset of the file test success.
64  * @tc.size   : MediumTest
65  * @tc.type   : Function
66  * @tc.level  : Level 1
67  */
HWTEST_F(LseekApiTest, LseekSetOffsetTestSuccess_0001, Function | MediumTest | Level1)68 HWTEST_F(LseekApiTest, LseekSetOffsetTestSuccess_0001, Function | MediumTest | Level1)
69 {
70     int fd = open(TEST_FILE, O_WRONLY | O_CREAT, 0644);
71     EXPECT_TRUE(fd > 0);
72 
73     // file middle position test
74     off_t offset = TEST_LEN / 2;
75     off_t pos = lseek(fd, offset, SEEK_SET);
76     EXPECT_EQ(pos, offset);
77 
78     // file start position test
79     offset = 0;
80     pos = lseek(fd, offset, SEEK_SET);
81     EXPECT_EQ(pos, offset);
82 
83     // file end position test
84     offset = TEST_LEN;
85     pos = lseek(fd, offset, SEEK_SET);
86     EXPECT_EQ(pos, offset);
87 
88     // position larger than file length test
89     offset = TEST_LEN * 2;
90     errno = 0;
91     pos = lseek(fd, offset, SEEK_SET);
92     EXPECT_EQ(pos, offset);
93 
94     close(fd);
95 }
96 
97 /*
98  * @tc.number : SUB_KERNEL_SYSCALL_LSEEK_0200
99  * @tc.name   : LseekSetNegativePositionFailed_0002
100  * @tc.desc   : lseek sets a negative position failed, errno EINVAL.
101  * @tc.size   : MediumTest
102  * @tc.type   : Function
103  * @tc.level  : Level 2
104  */
HWTEST_F(LseekApiTest, LseekSetNegativePositionFailed_0002, Function | MediumTest | Level2)105 HWTEST_F(LseekApiTest, LseekSetNegativePositionFailed_0002, Function | MediumTest | Level2)
106 {
107     int fd = open(TEST_FILE, O_WRONLY | O_CREAT, 0644);
108     EXPECT_TRUE(fd > 0);
109 
110     // -1 position test failed, errno EINVAL
111     off_t offset = -1;
112     errno = 0;
113     off_t pos = lseek(fd, offset, SEEK_SET);
114     EXPECT_EQ(pos, -1);
115     EXPECT_EQ(errno, EINVAL);
116     close(fd);
117 }
118 
119 /*
120  * @tc.number : SUB_KERNEL_SYSCALL_LSEEK_0300
121  * @tc.name   : LseekSEEK_CURTestSuccess_0003
122  * @tc.desc   : lseek set position from current pos success.
123  * @tc.size   : MediumTest
124  * @tc.type   : Function
125  * @tc.level  : Level 1
126  */
HWTEST_F(LseekApiTest, LseekSEEK_CURTestSuccess_0003, Function | MediumTest | Level1)127 HWTEST_F(LseekApiTest, LseekSEEK_CURTestSuccess_0003, Function | MediumTest | Level1)
128 {
129     int fd = open(TEST_FILE, O_WRONLY | O_CREAT, 0644);
130     EXPECT_TRUE(fd > 0);
131 
132     // set pos to middle position
133     off_t start = TEST_LEN / 2;
134     off_t initPos = lseek(fd, start, SEEK_SET);
135     EXPECT_EQ(initPos, start);
136 
137     // set positive pos to offset from current position
138     off_t offset = TEST_LEN / 2;
139     off_t pos = lseek(fd, offset, SEEK_CUR);
140     EXPECT_EQ(pos, initPos + offset);
141 
142     // set negative pos to offset from current position
143     offset = (TEST_LEN / 2) * (-1);
144     initPos = pos;
145     pos = lseek(fd, offset, SEEK_CUR);
146     EXPECT_EQ(pos, initPos + offset);
147 
148     // set positive pos to offset from current position
149     offset = TEST_LEN * 2;
150     initPos = pos;
151     pos = lseek(fd, offset, SEEK_CUR);
152     EXPECT_EQ(pos, initPos + offset);
153 
154     close(fd);
155 }
156 
157 /*
158  * @tc.number : SUB_KERNEL_SYSCALL_LSEEK_0400
159  * @tc.name   : LseekSEEK_CURNegativeTestFailed_0004
160  * @tc.desc   : lseek set negative position from current pos failed, errno EINVAL.
161  * @tc.size   : MediumTest
162  * @tc.type   : Function
163  * @tc.level  : Level 2
164  */
HWTEST_F(LseekApiTest, LseekSEEK_CURNegativeTestFailed_0004, Function | MediumTest | Level2)165 HWTEST_F(LseekApiTest, LseekSEEK_CURNegativeTestFailed_0004, Function | MediumTest | Level2)
166 {
167     int fd = open(TEST_FILE, O_WRONLY | O_CREAT, 0644);
168     EXPECT_TRUE(fd > 0);
169 
170     // set negative pos to offset from current position
171     off_t offset = -1;
172     errno = 0;
173     off_t pos = lseek(fd, offset, SEEK_CUR);
174     EXPECT_EQ(pos, -1);
175     EXPECT_EQ(errno, EINVAL);
176 
177     close(fd);
178 }
179 
180 /*
181  * @tc.number : SUB_KERNEL_SYSCALL_LSEEK_0500
182  * @tc.name   : LseekSEEK_ENDTestSuccess_0005
183  * @tc.desc   : lseek use SEEK_END set the position to file end success.
184  * @tc.size   : MediumTest
185  * @tc.type   : Function
186  * @tc.level  : Level 1
187  */
HWTEST_F(LseekApiTest, LseekSEEK_ENDTestSuccess_0005, Function | MediumTest | Level1)188 HWTEST_F(LseekApiTest, LseekSEEK_ENDTestSuccess_0005, Function | MediumTest | Level1)
189 {
190     int fd = open(TEST_FILE, O_WRONLY | O_CREAT, 0644);
191     EXPECT_TRUE(fd > 0);
192 
193     off_t pos = lseek(fd, 0, SEEK_END);
194     EXPECT_EQ(pos, TEST_LEN);
195 
196     close(fd);
197 }
198 
199 /*
200  * @tc.number : SUB_KERNEL_SYSCALL_LSEEK_0600
201  * @tc.name   : LseekInvalidFdTestFailed_0006
202  * @tc.desc   : lseek used invalid fd test failed, errno EBADF.
203  * @tc.size   : MediumTest
204  * @tc.type   : Function
205  * @tc.level  : Level 2
206  */
HWTEST_F(LseekApiTest, LseekInvalidFdTestFailed_0006, Function | MediumTest | Level2)207 HWTEST_F(LseekApiTest, LseekInvalidFdTestFailed_0006, Function | MediumTest | Level2)
208 {
209     errno = 0;
210     off_t pos = lseek(-1, 0, SEEK_SET);
211     EXPECT_EQ(pos, -1);
212     EXPECT_EQ(errno, EBADF);
213 }