2 * Copyright (c) 2017-2018, De Rais <derais@cock.li>
4 * Permission to use, copy, modify, and/or distribute this software for
5 * any purpose with or without fee is hereby granted, provided that the
6 * above copyright notice and this permission notice appear in all
9 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL
10 * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED
11 * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE
12 * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL
13 * DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
14 * PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
15 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
16 * PERFORMANCE OF THIS SOFTWARE.
24 #include <sys/types.h>
31 /* Try and acquire all lock files, in order */
32 static int try_get_all_lock_files(size_t num_boards
)
34 for (size_t j
= 0; j
< num_boards
; ++j
) {
35 if (lock_acquire(j
) < 0) {
43 /* Try and release all lock files, in order */
44 static int try_drop_all_lock_files(size_t num_boards
)
46 for (size_t j
= 0; j
< num_boards
; ++j
) {
53 /* Make sure we can write to the directory where all the www files will be */
54 static int try_write_work_dir(const char *work_dir
)
58 /* First, the directories should be there */
59 if (mkdir(work_dir
, 0755) < 0) {
60 if (errno
!= EEXIST
) {
61 PERROR_MESSAGE("mkdir");
62 ERROR_MESSAGE("Cannot create directory %s", work_dir
);
73 /* Make sure we can write to the directory where all the www files will be */
74 static int try_write_www_dir(const struct board
*boards
, size_t boards_num
,
75 const char *static_www_folder
)
82 /* First, the directories should be there */
83 for (size_t j
= 0; j
< boards_num
; ++j
) {
84 len
= snprintf(0, 0, "%s/%s", static_www_folder
,
88 ERROR_MESSAGE("overflow");
92 if (!(path
= malloc(len
+ 1))) {
93 PERROR_MESSAGE("malloc");
97 sprintf(path
, "%s/%s", static_www_folder
, boards
[j
].name
);
99 if (mkdir(path
, 0755) < 0) {
100 if (errno
!= EEXIST
) {
101 PERROR_MESSAGE("mkdir");
102 ERROR_MESSAGE("Cannot create directory %s",
112 /* The /recent page */
113 len
= snprintf(0, 0, "%s/recent", static_www_folder
);
116 ERROR_MESSAGE("overflow");
120 if (!(path
= malloc(len
+ 1))) {
121 PERROR_MESSAGE("malloc");
125 sprintf(path
, "%s/recent", static_www_folder
);
127 if (mkdir(path
, 0755) < 0) {
128 if (errno
!= EEXIST
) {
129 PERROR_MESSAGE("mkdir");
130 ERROR_MESSAGE("Cannot create directory %s", path
);
138 /* Now, the src/ and res/ dirs should be there */
139 for (size_t j
= 0; j
< boards_num
; ++j
) {
140 len
= snprintf(0, 0, "%s/%s/src", static_www_folder
,
144 ERROR_MESSAGE("overflow");
148 if (!(path
= malloc(len
+ 1))) {
149 PERROR_MESSAGE("malloc");
153 sprintf(path
, "%s/%s/src", static_www_folder
, boards
[j
].name
);
155 if (mkdir(path
, 0755) < 0) {
156 if (errno
!= EEXIST
) {
157 PERROR_MESSAGE("mkdir");
158 ERROR_MESSAGE("Cannot create directory %s",
164 sprintf(path
, "%s/%s/res", static_www_folder
, boards
[j
].name
);
166 if (mkdir(path
, 0755) < 0) {
167 if (errno
!= EEXIST
) {
168 PERROR_MESSAGE("mkdir");
169 ERROR_MESSAGE("Cannot create directory %s",
179 /* Now, we need to be able to write there */
180 for (size_t j
= 0; j
< boards_num
; ++j
) {
182 len
= snprintf(0, 0, "%s/%s/src/a", static_www_folder
,
186 ERROR_MESSAGE("overflow");
190 if (!(path
= malloc(len
+ 1))) {
191 PERROR_MESSAGE("malloc");
195 sprintf(path
, "%s/%s/src/a", static_www_folder
, boards
[j
].name
);
197 if (!(f
= fopen(path
, "a"))) {
198 PERROR_MESSAGE("fopen");
199 ERROR_MESSAGE("Cannot create dummy file %s", path
);
204 PERROR_MESSAGE("fclose");
205 ERROR_MESSAGE("Cannot close dummy file %s", path
);
210 sprintf(path
, "%s/%s/res/a", static_www_folder
, boards
[j
].name
);
212 if (!(f
= fopen(path
, "a"))) {
213 PERROR_MESSAGE("fopen");
214 ERROR_MESSAGE("Cannot create dummy file %s", path
);
219 PERROR_MESSAGE("fclose");
220 ERROR_MESSAGE("Cannot close dummy file %s", path
);
229 len
= snprintf(0, 0, "%s/recent/a", static_www_folder
);
232 ERROR_MESSAGE("overflow");
236 if (!(path
= malloc(len
+ 1))) {
237 PERROR_MESSAGE("malloc");
241 sprintf(path
, "%s/recent/a", static_www_folder
);
243 if (!(f
= fopen(path
, "a"))) {
244 PERROR_MESSAGE("fopen");
245 ERROR_MESSAGE("Cannot create dummy file %s", path
);
250 PERROR_MESSAGE("fclose");
251 ERROR_MESSAGE("Cannot close dummy file %s", path
);
264 * Returns < 0 in case something isn't set up right
268 * - conf is correctly set up.
270 * Postconditions (success):
272 * - The ZZZ_setup() functions in other files have all been called,
273 * and all returned successfully.
275 int preconditions_check(const struct configuration
*conf
)
279 uintmax_t max_size
= (size_t) -1;
281 for (j
= 0; j
< conf
->filetypes_num
; ++j
) {
282 const struct filetype
*f
= &conf
->filetypes
[j
];
284 if (f
->thumb_creation_command
&&
285 f
->static_thumbnail
) {
286 ERROR_MESSAGE("Filetype for %s cannot have both "
287 "thumb_creation_command and static_thumbnail",
292 if (!f
->thumb_creation_command
&&
293 !f
->static_thumbnail
) {
294 ERROR_MESSAGE("Filetype for %s must have one of "
295 "thumb_creation_command or static_thumbnail",
301 for (j
= 0; j
< conf
->boards_num
; ++j
) {
302 const struct board
*b
= &conf
->boards
[j
];
305 ERROR_MESSAGE("Board /%s/'s num_pages must be positive",
310 if (!b
->threads_per_page
) {
311 ERROR_MESSAGE("Board /%s/'s threads_per_page must be "
312 "positive", b
->name
);
316 if (b
->num_pages
* b
->threads_per_page
> max_size
) {
317 ERROR_MESSAGE("Board /%s/'s threads cannot be "
318 "fit in memory", b
->name
);
322 if (!strcmp(b
->name
, "recent")) {
323 ERROR_MESSAGE("The board name /recent/ is reserved");
328 if (try_write_work_dir(conf
->work_path
) < 0) {
332 if (setup_multipart() < 0) {
336 if (setup_sanitize_comment(conf
) < 0) {
340 if (setup_sanitize_file(conf
) < 0) {
344 if (setup_tripcodes(conf
) < 0) {
348 if (setup_locks(conf
) < 0) {
352 if (setup_write_thread(conf
) < 0) {
356 if (try_get_all_lock_files(conf
->boards_num
) < 0) {
360 /* Since we have the lock files now, we need not fear races */
361 if (setup_dbs(conf
) < 0) {
365 if (try_write_www_dir(conf
->boards
, conf
->boards_num
,
366 conf
->static_www_folder
) < 0) {
373 if (try_drop_all_lock_files(conf
->boards_num
) < 0) {