Whamcloud - gitweb
LU-6142 tests: Fix style issues for chownmany.c
[fs/lustre-release.git] / lustre / tests / flock.c
1 /*
2  * GPL HEADER START
3  *
4  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License version 2 only,
8  * as published by the Free Software Foundation.
9  *
10  * This program is distributed in the hope that it will be useful, but
11  * WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
13  * General Public License version 2 for more details (a copy is included
14  * in the LICENSE file that accompanied this code).
15  *
16  * You should have received a copy of the GNU General Public License
17  * version 2 along with this program; If not, see
18  * http://www.gnu.org/licenses/gpl-2.0.html
19  *
20  * GPL HEADER END
21  */
22 /*
23  * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
24  * Use is subject to license terms.
25  *
26  * Copyright (c) 2015, Intel Corporation.
27  */
28 /*
29  * This file is part of Lustre, http://www.lustre.org/
30  * Lustre is a trademark of Sun Microsystems, Inc.
31  *
32  * lustre/tests/flock.c
33  *
34  * Lustre Light user test program
35  */
36
37 #define _BSD_SOURCE
38
39 #include <stdio.h>
40 #include <stdlib.h>
41 #include <unistd.h>
42 #include <getopt.h>
43 #include <string.h>
44 #include <sys/types.h>
45 #include <sys/stat.h>
46 #include <fcntl.h>
47 #include <sys/queue.h>
48 #include <signal.h>
49 #include <errno.h>
50 #include <dirent.h>
51 #include <sys/uio.h>
52 #include <sys/time.h>
53 #include <stdarg.h>
54
55 static char lustre_path[] = "/mnt/lustre";
56
57 #define ENTRY(str)                                                      \
58         do {                                                            \
59                 char buf[100];                                          \
60                 int len;                                                \
61                 sprintf(buf, "===== START %s: %s ", __FUNCTION__, (str)); \
62                 len = strlen(buf);                                      \
63                 if (len < 79) {                                         \
64                         memset(buf+len, '=', 100-len);                  \
65                         buf[79] = '\n';                                 \
66                         buf[80] = 0;                                    \
67                 }                                                       \
68                 printf("%s", buf);                                      \
69         } while (0)
70
71 #define LEAVE()                                                         \
72         do {                                                            \
73                 char buf[100];                                          \
74                 int len;                                                \
75                 sprintf(buf, "===== END TEST %s: successfully ",        \
76                         __FUNCTION__);                                  \
77                 len = strlen(buf);                                      \
78                 if (len < 79) {                                         \
79                         memset(buf+len, '=', 100-len);                  \
80                         buf[79] = '\n';                                 \
81                         buf[80] = 0;                                    \
82                 }                                                       \
83                 printf("%s", buf);                                      \
84         } while (0)
85
86 #define EXIT return
87
88 #define MAX_PATH_LENGTH 4096
89
90
91 int t_fcntl(int fd, int cmd, ...)
92 {
93         va_list ap;
94         long arg;
95         struct flock *lock;
96         int rc = -1;
97
98         va_start(ap, cmd);
99         switch (cmd) {
100         case F_GETFL:
101                 va_end(ap);
102                 rc = fcntl(fd, cmd);
103                 if (rc == -1) {
104                         printf("fcntl GETFL failed: %s\n",
105                                  strerror(errno));
106                         EXIT(1);
107                 }
108                 break;
109         case F_SETFL:
110                 arg = va_arg(ap, long);
111                 va_end(ap);
112                 rc = fcntl(fd, cmd, arg);
113                 if (rc == -1) {
114                         printf("fcntl SETFL %ld failed: %s\n",
115                                  arg, strerror(errno));
116                         EXIT(1);
117                 }
118                 break;
119         case F_GETLK:
120         case F_SETLK:
121         case F_SETLKW:
122                 lock = va_arg(ap, struct flock *);
123                 va_end(ap);
124                 rc = fcntl(fd, cmd, lock);
125                 if (rc == -1) {
126                         printf("fcntl cmd %d failed: %s\n",
127                                  cmd, strerror(errno));
128                         EXIT(1);
129                 }
130                 break;
131         case F_DUPFD:
132                 arg = va_arg(ap, long);
133                 va_end(ap);
134                 rc = fcntl(fd, cmd, arg);
135                 if (rc == -1) {
136                         printf("fcntl F_DUPFD %d failed: %s\n",
137                                  (int)arg, strerror(errno));
138                         EXIT(1);
139                 }
140                 break;
141         default:
142                 va_end(ap);
143                 printf("fcntl cmd %d not supported\n", cmd);
144                 EXIT(1);
145         }
146         printf("fcntl %d = %d, ltype = %d\n", cmd, rc, lock->l_type);
147         return rc;
148 }
149
150 int t_unlink(const char *path)
151 {
152         int rc;
153
154         rc = unlink(path);
155         if (rc) {
156                 printf("unlink(%s) error: %s\n", path, strerror(errno));
157                 EXIT(-1);
158         }
159         return rc;
160 }
161
162 void t21()
163 {
164         char file[MAX_PATH_LENGTH] = "";
165         int fd, ret;
166         struct flock lock = {
167                 .l_type = F_RDLCK,
168                 .l_whence = SEEK_SET,
169         };
170
171         ENTRY("basic fcntl support");
172         snprintf(file, MAX_PATH_LENGTH, "%s/test_t21_file", lustre_path);
173
174         fd = open(file, O_RDWR|O_CREAT, (mode_t)0666);
175         if (fd < 0) {
176                 printf("open(%s) error: %s\n", file, strerror(errno));
177                 exit(-1);
178         }
179
180         t_fcntl(fd, F_SETFL, O_APPEND);
181         if (!(ret = t_fcntl(fd, F_GETFL)) & O_APPEND) {
182                 printf("error get flag: ret %x\n", ret);
183                 exit(-1);
184         }
185
186         t_fcntl(fd, F_SETLK, &lock);
187         t_fcntl(fd, F_GETLK, &lock);
188         lock.l_type = F_WRLCK;
189         t_fcntl(fd, F_SETLKW, &lock);
190         t_fcntl(fd, F_GETLK, &lock);
191         lock.l_type = F_UNLCK;
192         t_fcntl(fd, F_SETLK, &lock);
193
194         close(fd);
195         t_unlink(file);
196         LEAVE();
197 }
198
199
200 int main(int argc, char * const argv[])
201 {
202         /* Set D_VFSTRACE to see messages from ll_file_flock.
203            The test passes either with -o flock or -o noflock 
204            mount -o flock -t lustre uml1:/mds1/client /mnt/lustre */
205         t21();
206
207         printf("completed successfully\n");
208         return 0;
209 }