glusterfs

Форк
0
352 строки · 8.7 Кб
1
/*
2
  Copyright (c) 2008-2012 Red Hat, Inc. <http://www.redhat.com>
3
  This file is part of GlusterFS.
4

5
  This file is licensed to you under your choice of the GNU Lesser
6
  General Public License, version 3 or any later version (LGPLv3 or
7
  later), or the GNU General Public License, version 2 (GPLv2), in all
8
  cases as published by the Free Software Foundation.
9
*/
10

11
#include <pthread.h>
12

13
#include "glusterfs/syncop.h"
14
#include "glusterfs/libglusterfs-messages.h"
15

16
const char *gf_fop_list[GF_FOP_MAXVALUE] = {
17
    [GF_FOP_NULL] = "NULL",
18
    [GF_FOP_STAT] = "STAT",
19
    [GF_FOP_READLINK] = "READLINK",
20
    [GF_FOP_MKNOD] = "MKNOD",
21
    [GF_FOP_MKDIR] = "MKDIR",
22
    [GF_FOP_UNLINK] = "UNLINK",
23
    [GF_FOP_RMDIR] = "RMDIR",
24
    [GF_FOP_SYMLINK] = "SYMLINK",
25
    [GF_FOP_RENAME] = "RENAME",
26
    [GF_FOP_LINK] = "LINK",
27
    [GF_FOP_TRUNCATE] = "TRUNCATE",
28
    [GF_FOP_OPEN] = "OPEN",
29
    [GF_FOP_READ] = "READ",
30
    [GF_FOP_WRITE] = "WRITE",
31
    [GF_FOP_STATFS] = "STATFS",
32
    [GF_FOP_FLUSH] = "FLUSH",
33
    [GF_FOP_FSYNC] = "FSYNC",
34
    [GF_FOP_SETXATTR] = "SETXATTR",
35
    [GF_FOP_GETXATTR] = "GETXATTR",
36
    [GF_FOP_REMOVEXATTR] = "REMOVEXATTR",
37
    [GF_FOP_OPENDIR] = "OPENDIR",
38
    [GF_FOP_FSYNCDIR] = "FSYNCDIR",
39
    [GF_FOP_ACCESS] = "ACCESS",
40
    [GF_FOP_CREATE] = "CREATE",
41
    [GF_FOP_FTRUNCATE] = "FTRUNCATE",
42
    [GF_FOP_FSTAT] = "FSTAT",
43
    [GF_FOP_LK] = "LK",
44
    [GF_FOP_LOOKUP] = "LOOKUP",
45
    [GF_FOP_READDIR] = "READDIR",
46
    [GF_FOP_INODELK] = "INODELK",
47
    [GF_FOP_FINODELK] = "FINODELK",
48
    [GF_FOP_ENTRYLK] = "ENTRYLK",
49
    [GF_FOP_FENTRYLK] = "FENTRYLK",
50
    [GF_FOP_XATTROP] = "XATTROP",
51
    [GF_FOP_FXATTROP] = "FXATTROP",
52
    [GF_FOP_FSETXATTR] = "FSETXATTR",
53
    [GF_FOP_FGETXATTR] = "FGETXATTR",
54
    [GF_FOP_RCHECKSUM] = "RCHECKSUM",
55
    [GF_FOP_SETATTR] = "SETATTR",
56
    [GF_FOP_FSETATTR] = "FSETATTR",
57
    [GF_FOP_READDIRP] = "READDIRP",
58
    [GF_FOP_GETSPEC] = "GETSPEC",
59
    [GF_FOP_FORGET] = "FORGET",
60
    [GF_FOP_RELEASE] = "RELEASE",
61
    [GF_FOP_RELEASEDIR] = "RELEASEDIR",
62
    [GF_FOP_FREMOVEXATTR] = "FREMOVEXATTR",
63
    [GF_FOP_FALLOCATE] = "FALLOCATE",
64
    [GF_FOP_DISCARD] = "DISCARD",
65
    [GF_FOP_ZEROFILL] = "ZEROFILL",
66
    [GF_FOP_IPC] = "IPC",
67
    [GF_FOP_SEEK] = "SEEK",
68
    [GF_FOP_LEASE] = "LEASE",
69
    [GF_FOP_COMPOUND] = "COMPOUND",
70
    [GF_FOP_GETACTIVELK] = "GETACTIVELK",
71
    [GF_FOP_SETACTIVELK] = "SETACTIVELK",
72
    [GF_FOP_PUT] = "PUT",
73
    [GF_FOP_ICREATE] = "ICREATE",
74
    [GF_FOP_NAMELINK] = "NAMELINK",
75
    [GF_FOP_COPY_FILE_RANGE] = "COPY_FILE_RANGE",
76
};
77

78
const char *gf_upcall_list[GF_UPCALL_FLAGS_MAXVALUE] = {
79
    [GF_UPCALL_NULL] = "NULL",
80
    [GF_UPCALL] = "UPCALL",
81
    [GF_UPCALL_CI_STAT] = "CI_IATT",
82
    [GF_UPCALL_CI_XATTR] = "CI_XATTR",
83
    [GF_UPCALL_CI_RENAME] = "CI_RENAME",
84
    [GF_UPCALL_CI_NLINK] = "CI_UNLINK",
85
    [GF_UPCALL_CI_FORGET] = "CI_FORGET",
86
    [GF_UPCALL_LEASE_RECALL] = "LEASE_RECALL",
87
};
88

89
/* THIS */
90

91
/* This global ctx is a bad hack to prevent some of the libgfapi crashes.
92
 * This should be removed once the patch on resource pool is accepted
93
 */
94
pthread_mutex_t global_ctx_mutex = PTHREAD_MUTEX_INITIALIZER;
95
xlator_t global_xlator;
96
static int gf_global_mem_acct_enable = 1;
97
static pthread_once_t globals_inited = PTHREAD_ONCE_INIT;
98

99
static pthread_key_t free_key;
100

101
static __thread xlator_t *thread_xlator = NULL;
102
static __thread void *thread_synctask = NULL;
103
static __thread void *thread_leaseid = NULL;
104
static __thread struct syncopctx thread_syncopctx = {};
105
static __thread char thread_uuid_buf[GF_UUID_BUF_SIZE] = {};
106
static __thread char thread_lkowner_buf[GF_LKOWNER_BUF_SIZE] = {};
107
static __thread char thread_leaseid_buf[GF_LEASE_ID_BUF_SIZE] = {};
108

109
int
110
gf_global_mem_acct_enable_get(void)
111
{
112
    return gf_global_mem_acct_enable;
113
}
114

115
int
116
gf_global_mem_acct_enable_set(int val)
117
{
118
    gf_global_mem_acct_enable = val;
119
    return 0;
120
}
121

122
static struct xlator_cbks global_cbks = {
123
    .forget = NULL,
124
    .release = NULL,
125
    .releasedir = NULL,
126
    .invalidate = NULL,
127
    .client_destroy = NULL,
128
    .client_disconnect = NULL,
129
    .ictxmerge = NULL,
130
    .ictxsize = NULL,
131
    .fdctxsize = NULL,
132
};
133

134
/* This is required to get through the check in graph.c */
135
static struct xlator_fops global_fops = {};
136

137
static int
138
global_xl_reconfigure(xlator_t *this, dict_t *options)
139
{
140
    int ret = -1;
141
    gf_boolean_t bool_opt = _gf_false;
142

143
    /* This is not added in volume dump, hence adding the options in log
144
       would be helpful for debugging later */
145
    dict_dump_to_log(options);
146

147
    GF_OPTION_RECONF("measure-latency", bool_opt, options, bool, out);
148
    this->ctx->measure_latency = bool_opt;
149

150
    GF_OPTION_RECONF("metrics-dump-path", this->ctx->config.metrics_dumppath,
151
                     options, str, out);
152

153
    /* TODO: add more things here */
154
    ret = 0;
155
out:
156
    return ret;
157
}
158

159
static int
160
global_xl_init(xlator_t *this)
161
{
162
    int ret = -1;
163
    gf_boolean_t bool_opt = false;
164

165
    GF_OPTION_INIT("measure-latency", bool_opt, bool, out);
166
    this->ctx->measure_latency = bool_opt;
167

168
    GF_OPTION_INIT("metrics-dump-path", this->ctx->config.metrics_dumppath, str,
169
                   out);
170

171
    ret = 0;
172

173
out:
174
    return ret;
175
}
176

177
static void
178
global_xl_fini(xlator_t *this)
179
{
180
    return;
181
}
182

183
struct volume_options global_xl_options[] = {
184
    {.key = {"measure-latency"},
185
     .type = GF_OPTION_TYPE_BOOL,
186
     .default_value = "no",
187
     .op_version = {GD_OP_VERSION_4_0_0},
188
     .flags = OPT_FLAG_SETTABLE,
189
     .tags = {"global", "context"},
190
     .description = "Use this option to toggle measuring latency"},
191
    {.key = {"metrics-dump-path"},
192
     .type = GF_OPTION_TYPE_STR,
193
     .default_value = "{{gluster_workdir}}/metrics",
194
     .op_version = {GD_OP_VERSION_4_0_0},
195
     .flags = OPT_FLAG_SETTABLE,
196
     .tags = {"global", "context"},
197
     .description = "Use this option to set the metrics dump path"},
198

199
    {
200
        .key = {NULL},
201
    },
202
};
203

204
static volume_opt_list_t global_xl_opt_list;
205

206
void
207
glusterfs_this_init(void)
208
{
209
    global_xlator.name = "glusterfs";
210
    global_xlator.type = GF_GLOBAL_XLATOR_NAME;
211
    global_xlator.cbks = &global_cbks;
212
    global_xlator.fops = &global_fops;
213
    global_xlator.reconfigure = global_xl_reconfigure;
214
    global_xlator.init = global_xl_init;
215
    global_xlator.fini = global_xl_fini;
216

217
    INIT_LIST_HEAD(&global_xlator.volume_options);
218
    INIT_LIST_HEAD(&global_xl_opt_list.list);
219
    global_xl_opt_list.given_opt = global_xl_options;
220

221
    list_add_tail(&global_xl_opt_list.list, &global_xlator.volume_options);
222
}
223

224
xlator_t **
225
__glusterfs_this_location(void)
226
{
227
    xlator_t **this_location;
228

229
    this_location = &thread_xlator;
230
    if (*this_location == NULL) {
231
        thread_xlator = &global_xlator;
232
    }
233
    return this_location;
234
}
235

236
/* SYNCOPCTX */
237

238
void *
239
syncopctx_getctx(void)
240
{
241
    return &thread_syncopctx;
242
}
243

244
/* SYNCTASK */
245

246
void *
247
synctask_get(void)
248
{
249
    return thread_synctask;
250
}
251

252
void
253
synctask_set(void *synctask)
254
{
255
    thread_synctask = synctask;
256
}
257

258
// UUID_BUFFER
259

260
char *
261
glusterfs_uuid_buf_get(void)
262
{
263
    return thread_uuid_buf;
264
}
265

266
/* LKOWNER_BUFFER */
267

268
char *
269
glusterfs_lkowner_buf_get(void)
270
{
271
    return thread_lkowner_buf;
272
}
273

274
/* Leaseid buffer */
275

276
char *
277
glusterfs_leaseid_buf_get(void)
278
{
279
    char *buf = NULL;
280

281
    buf = thread_leaseid;
282
    if (buf == NULL) {
283
        buf = thread_leaseid_buf;
284
        thread_leaseid = buf;
285
    }
286

287
    return buf;
288
}
289

290
char *
291
glusterfs_leaseid_exist(void)
292
{
293
    return thread_leaseid;
294
}
295

296
static void
297
glusterfs_cleanup(void *ptr)
298
{
299
    if (thread_syncopctx.groups != NULL) {
300
        GF_FREE(thread_syncopctx.groups);
301
    }
302

303
    mem_pool_thread_destructor(NULL);
304
}
305

306
void
307
gf_thread_needs_cleanup(void)
308
{
309
    /* The value stored in free_key TLS is not really used for anything, but
310
     * pthread implementation doesn't call the TLS destruction function unless
311
     * it's != NULL. This function must be called whenever something is
312
     * allocated for this thread so that glusterfs_cleanup() will be called
313
     * and resources can be released. */
314
    (void)pthread_setspecific(free_key, (void *)1);
315
}
316

317
static void
318
gf_globals_init_once(void)
319
{
320
    int ret = 0;
321

322
    glusterfs_this_init();
323

324
    /* This is needed only to cleanup the potential allocation of
325
     * thread_syncopctx.groups. */
326
    ret = pthread_key_create(&free_key, glusterfs_cleanup);
327
    if (ret != 0) {
328
        gf_msg("", GF_LOG_ERROR, ret, LG_MSG_PTHREAD_KEY_CREATE_FAILED,
329
               "failed to create the pthread key");
330

331
        gf_msg("", GF_LOG_CRITICAL, 0, LG_MSG_GLOBAL_INIT_FAILED,
332
               "Exiting as global initialization failed");
333

334
        exit(ret);
335
    }
336
}
337

338
int
339
glusterfs_globals_init(glusterfs_ctx_t *ctx)
340
{
341
    int ret = 0;
342

343
    gf_log_globals_init(ctx, GF_LOG_INFO);
344

345
    ret = pthread_once(&globals_inited, gf_globals_init_once);
346

347
    if (ret)
348
        gf_msg("", GF_LOG_CRITICAL, ret, LG_MSG_PTHREAD_FAILED,
349
               "pthread_once failed");
350

351
    return ret;
352
}
353

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.