]> git.ipfire.org Git - thirdparty/xfsprogs-dev.git/blame - quota/init.c
xfs: fix maxicount division by zero error
[thirdparty/xfsprogs-dev.git] / quota / init.c
CommitLineData
959ef981 1// SPDX-License-Identifier: GPL-2.0
5aead01d 2/*
da23017d
NS
3 * Copyright (c) 2003-2005 Silicon Graphics, Inc.
4 * All Rights Reserved.
5aead01d
NS
5 */
6
42b4c8e8 7#include "libfrog/paths.h"
6b803e5a
CH
8#include "command.h"
9#include "input.h"
5aead01d
NS
10#include "init.h"
11
12char *progname;
13int exitcode;
14int expert;
29647c8d 15bool foreign_allowed = false;
5aead01d
NS
16
17static char **projopts; /* table of project names (cmdline) */
18static int nprojopts; /* number of entries in name table. */
19
20static void
21add_project_opt(
22 char *optarg)
23{
24 nprojopts++;
25 projopts = realloc(projopts, sizeof(char*) * nprojopts);
26 if (!projopts) {
27 perror("realloc");
28 exit(1);
29 }
30 projopts[nprojopts - 1] = optarg;
31}
32
33static void
34usage(void)
35{
36 fprintf(stderr,
29647c8d 37 _("Usage: %s [-V] [-x] [-f] [-p prog] [-c cmd]... [-d project]... [path]\n"),
5aead01d
NS
38 progname);
39 exit(1);
40}
41
42void
43init_cvtnum(
cb7ba2b0
CH
44 unsigned int *blocksize,
45 unsigned int *sectsize)
5aead01d
NS
46{
47 *blocksize = 4096;
48 *sectsize = 512;
49}
50
51static void
52init_commands(void)
53{
54 edit_init();
55 free_init();
56 help_init();
57 path_init();
58 project_init();
59 quot_init();
60 quota_init();
61 quit_init();
62 report_init();
63 state_init();
64}
65
ef346a25
DC
66/*
67 * This function allows xfs_quota commands to iterate across all discovered
68 * quota enabled filesystems. Commands that should not iterate all filesystems
69 * should specify CMD_FLAG_ONESHOT in their command flags.
70 */
5aead01d 71static int
ef346a25 72filesystem_iterator(
5aead01d
NS
73 int index)
74{
75 if (index >= fs_count)
76 return 0;
77
78 do {
79 fs_path = &fs_table[index++];
29647c8d
BD
80 /* skip project quota entries */
81 if ((fs_path->fs_flags & FS_PROJECT_PATH))
82 continue;
83
84 /* only consider foreign filesystems if told so */
85 if (!foreign_allowed && (fs_path->fs_flags & FS_FOREIGN))
86 continue;
87
88 /* We can use this one */
89 break;
90 } while (index < fs_count);
5aead01d 91
fa13a00f
NS
92 if (fs_path->fs_flags & FS_PROJECT_PATH)
93 return 0;
29647c8d
BD
94 if (!foreign_allowed && (fs_path->fs_flags & FS_FOREIGN))
95 return 0;
5aead01d
NS
96 if (index > fs_count)
97 return 0;
98 return index;
99}
100
29647c8d
BD
101static int
102init_check_command(
103 const cmdinfo_t *ct)
104{
b20b6c22
BD
105 if (!fs_path)
106 return 1;
107
2ba39cd3 108 /* If it's an XFS filesystem, always run the command. */
b20b6c22
BD
109 if (!(fs_path->fs_flags & FS_FOREIGN))
110 return 1;
111
2ba39cd3 112 /* If the user specified foreign filesystems are ok (-f), run cmd. */
b20b6c22
BD
113 if (foreign_allowed &&
114 (ct->flags & CMD_FLAG_FOREIGN_OK))
115 return 1;
116
2ba39cd3
BD
117 /* If cmd not allowed on foreign fs, regardless of -f flag, skip it. */
118 if (!(ct->flags & CMD_FLAG_FOREIGN_OK)) {
119 fprintf(stderr, _("%s: command is for XFS filesystems only\n"),
120 ct->name);
121 return 0;
122 }
123
124 /* foreign fs, but cmd only allowed via -f flag. Skip it. */
125 fprintf(stderr,
126 _("%s: foreign filesystem. Invoke xfs_quota with -f to enable.\n"),
b20b6c22
BD
127 ct->name);
128 return 0;
29647c8d
BD
129}
130
5aead01d
NS
131static void
132init(
133 int argc,
134 char **argv)
135{
136 int c;
137
138 progname = basename(argv[0]);
139 setlocale(LC_ALL, "");
140 bindtextdomain(PACKAGE, LOCALEDIR);
141 textdomain(PACKAGE);
142
29647c8d 143 while ((c = getopt(argc, argv, "c:d:D:fP:p:t:xV")) != EOF) {
5aead01d
NS
144 switch (c) {
145 case 'c': /* commands */
146 add_user_command(optarg);
147 break;
148 case 'd':
149 add_project_opt(optarg);
150 break;
29647c8d
BD
151 case 'f':
152 foreign_allowed = true;
88dabc17 153 break;
5aead01d
NS
154 case 't':
155 mtab_file = optarg;
156 break;
157 case 'D':
158 projects_file = optarg;
159 break;
160 case 'P':
161 projid_file = optarg;
162 break;
163 case 'p':
164 progname = optarg;
165 break;
166 case 'x':
167 expert++;
168 break;
169 case 'V':
170 printf(_("%s version %s\n"), progname, VERSION);
171 exit(0);
172 default:
173 usage();
174 }
175 }
176
0900efe4
AE
177 fs_table_initialise(argc - optind, &argv[optind], nprojopts, projopts);
178 free(projopts);
5aead01d
NS
179
180 init_commands();
ef346a25 181 add_command_iterator(filesystem_iterator);
29647c8d 182 add_check_command(init_check_command);
36298cce
DC
183
184 /*
185 * Ensure that global commands don't end up with an invalid path pointer
186 * by setting the default device at the first specified on the CLI
187 */
188 if (argc != optind)
189 fs_path = fs_table_lookup(argv[optind], FS_MOUNT_POINT);
190 else
191 fs_path = &fs_table[0];
5aead01d
NS
192}
193
194int
195main(
196 int argc,
197 char **argv)
198{
199 init(argc, argv);
200 command_loop();
201 return exitcode;
202}