smbstatus: add frame files for json specific methods
[Samba.git] / source3 / wscript
blob2121b8b6510d3daf234a2bef83a087c3e3588903
1 #!/usr/bin/env python
3 srcdir = ".."
5 import sys, os
6 from optparse import SUPPRESS_HELP
7 sys.path.insert(0, srcdir + "/buildtools/wafsamba")
8 sys.path.insert(0, "source3")
10 from waflib import Options, Logs, Errors
11 import wafsamba
12 import build.charset
13 from wafsamba import samba_utils
14 from samba_utils import TO_LIST
15 import samba3
17 default_prefix = Options.default_prefix = '/usr/local/samba'
19 def options(opt):
21 opt.add_option('--with-static-modules',
22 help=("Comma-separated list of names of modules to statically link in. "+
23 "May include !module to disable 'module'. "+
24 "Can be '!FORCED' to disable all non-required static only modules. "+
25 "Can be '!DEFAULT' to disable all modules defaulting to a static build. "+
26 "Can be 'ALL' to build all default shared modules static. "+
27 "The most specific one wins, while the order is ignored "+
28 "and --with-static-modules is evaluated before "+
29 "--with-shared-modules"),
30 action="store", dest='static_modules', default=None)
31 opt.add_option('--with-shared-modules',
32 help=("Comma-separated list of names of modules to build shared. "+
33 "May include !module to disable 'module'. "+
34 "Can be '!FORCED' to disable all non-required shared only modules. "+
35 "Can be '!DEFAULT' to disable all modules defaulting to a shared build. "+
36 "Can be 'ALL' to build all default static modules shared. "+
37 "The most specific one wins, while the order is ignored "+
38 "and --with-static-modules is evaluated before "+
39 "--with-shared-modules"),
40 action="store", dest='shared_modules', default=None)
42 # Optional Libraries
43 # ------------------
45 # Most of the calls to opt.samba_add_onoff_option() implicitly
46 # or explicity use default=True
48 # To assist users and distributors to build Samba with the full feature
49 # set, the build system will abort if our dependent libraries and their
50 # header files are not found on the target system. This will mean for
51 # example, that xattr, acl and ldap headers must be installed for the
52 # default build to complete. The configure system will check for these
53 # headers, and the error message will indicate the option (such as
54 # --without-acl-support) that can be specified to skip this requirement.
56 # This will assist users and in particular distributors in building fully
57 # functional packages, while allowing those on systems truly without these
58 # facilities to continue to build Samba after careful consideration.
60 # It also ensures our container image generation in bootstrap/ is correct
61 # as otherwise a missing package there would just silently work
63 opt.samba_add_onoff_option('winbind')
64 opt.samba_add_onoff_option('ads')
65 opt.samba_add_onoff_option('ldap')
66 opt.samba_add_onoff_option('cups', with_name="enable", without_name="disable")
67 opt.samba_add_onoff_option('iprint', with_name="enable", without_name="disable")
68 opt.samba_add_onoff_option('pam')
69 opt.samba_add_onoff_option('quotas', default=None)
70 opt.samba_add_onoff_option('sendfile-support', default=None)
71 opt.samba_add_onoff_option('utmp')
72 opt.samba_add_onoff_option('avahi', with_name="enable", without_name="disable")
73 opt.samba_add_onoff_option('iconv')
74 opt.samba_add_onoff_option('acl-support')
75 opt.samba_add_onoff_option('syslog')
76 opt.samba_add_onoff_option('automount')
77 opt.samba_add_onoff_option('dmapi', default=None) # None means autodetection
78 opt.samba_add_onoff_option('fam', default=None) # None means autodetection
79 opt.samba_add_onoff_option('profiling-data', default=False)
80 opt.samba_add_onoff_option('libarchive', default=True)
82 opt.samba_add_onoff_option('cluster-support', default=False)
84 opt.samba_add_onoff_option('regedit', default=None)
85 opt.samba_add_onoff_option('winexe', default=None)
87 opt.samba_add_onoff_option('fake-kaserver',
88 help=("Include AFS fake-kaserver support"), default=False)
90 opt.add_option('--with-libcephfs',
91 help=("Directory under which libcephfs is installed"),
92 action="store", dest='libcephfs_dir', default=None)
94 opt.samba_add_onoff_option('glusterfs', with_name="enable", without_name="disable", default=True)
95 opt.samba_add_onoff_option('cephfs', with_name="enable", without_name="disable", default=True)
97 opt.add_option('--enable-vxfs',
98 help=("enable support for VxFS (default=no)"),
99 action="store_true", dest='enable_vxfs', default=False)
101 # default = None means autodetection
102 opt.samba_add_onoff_option('spotlight', with_name="enable", without_name="disable", default=None)
104 def configure(conf):
105 default_static_modules = []
106 default_shared_modules = []
107 required_static_modules = []
108 forced_static_modules = []
109 forced_shared_modules = []
111 if Options.options.developer:
112 conf.ADD_CFLAGS('-DDEVELOPER -DDEBUG_PASSWORD')
113 conf.env.developer = True
115 if sys.platform != 'openbsd5':
116 conf.ADD_LDFLAGS("-Wl,--export-dynamic", testflags=True)
118 # We crash without vfs_default
119 # and vfs_not_implemented provides helper function
120 # for other modules
121 required_static_modules.extend(['vfs_default', 'vfs_not_implemented'])
123 conf.CHECK_HEADERS('netdb.h')
124 conf.CHECK_HEADERS('linux/falloc.h linux/ioctl.h')
126 conf.CHECK_FUNCS('getcwd fchown chmod fchmod mknod mknodat')
127 conf.CHECK_FUNCS('strtol strchr strupr chflags fchflags')
128 conf.CHECK_FUNCS('getrlimit fsync setpgid')
129 conf.CHECK_FUNCS('setsid glob strpbrk crypt16 getauthuid')
130 conf.CHECK_FUNCS('innetgr')
131 conf.CHECK_FUNCS('initgroups select poll rdchk getgrnam getgrent pathconf')
132 conf.CHECK_FUNCS('setpriv setgidx setuidx setgroups syscall sysconf')
133 conf.CHECK_FUNCS('atexit grantpt posix_openpt fallocate')
134 conf.CHECK_FUNCS('fseeko setluid')
135 conf.CHECK_FUNCS('getpwnam', headers='sys/types.h pwd.h')
136 conf.CHECK_FUNCS('fdopendir')
137 conf.CHECK_FUNCS('getpwent_r setenv clearenv strcasecmp')
138 conf.CHECK_FUNCS('syslog vsyslog timegm setlocale')
139 conf.CHECK_FUNCS('lutimes utimensat futimens')
140 conf.CHECK_FUNCS('mlock munlock mlockall munlockall')
141 conf.CHECK_FUNCS('memalign posix_memalign hstrerror')
142 conf.CHECK_FUNCS('getdomainname')
143 conf.CHECK_FUNCS_IN('dn_expand _dn_expand __dn_expand', 'resolv')
144 conf.CHECK_FUNCS_IN('dn_expand', 'inet')
145 conf.CHECK_DECLS('readahead', reverse=True, headers='fcntl.h')
147 if conf.CHECK_CODE('''
148 #if defined(HAVE_UNISTD_H)
149 #include <unistd.h>
150 #endif
151 long ret = splice(0,0,1,0,400,SPLICE_F_MOVE);
152 ''',
153 'HAVE_LINUX_SPLICE',
154 headers='fcntl.h'):
155 conf.CHECK_DECLS('splice', reverse=True, headers='fcntl.h')
157 # Check for inotify support (Skip if we are SunOS)
158 #NOTE: illumos provides sys/inotify.h but is not an exact match for linux
159 host_os = sys.platform
160 if host_os.rfind('sunos') == -1:
161 conf.CHECK_HEADERS('sys/inotify.h')
162 if conf.env.HAVE_SYS_INOTIFY_H:
163 conf.DEFINE('HAVE_INOTIFY', 1)
165 # Check for Linux kernel oplocks
166 if conf.CHECK_DECLS('F_SETLEASE', headers='linux/fcntl.h', reverse=True):
167 conf.DEFINE('HAVE_KERNEL_OPLOCKS_LINUX', 1)
169 # check for fam libs
170 samba_fam_libs=None
171 check_for_fam=False
172 if Options.options.with_fam is None:
173 check_for_fam=True
174 elif Options.options.with_fam == True:
175 check_for_fam=True
177 if check_for_fam and conf.CHECK_HEADERS('fam.h'):
178 if conf.CHECK_FUNCS_IN('FAMOpen2', 'fam'):
179 samba_fam_libs='fam'
180 elif conf.CHECK_FUNCS_IN('FAMOpen2', 'fam C'):
181 samba_fam_libs='fam C'
182 conf.CHECK_TYPE('enum FAMCodes', headers='fam.h',
183 define='HAVE_FAM_H_FAMCODES_TYPEDEF',
184 msg='Checking whether enum FAMCodes is available')
185 conf.CHECK_FUNCS_IN('FAMNoExists', 'fam')
187 if samba_fam_libs is not None:
188 conf.DEFINE('SAMBA_FAM_LIBS', samba_fam_libs)
189 conf.DEFINE('HAVE_FAM', 1)
190 else:
191 if Options.options.with_fam == True:
192 conf.fatal('FAM support requested, but no suitable FAM library found')
193 elif check_for_fam:
194 Logs.warn('no suitable FAM library found')
196 # check for libarchive (tar command in smbclient)
197 # None means autodetect, True/False means enable/disable
198 conf.SET_TARGET_TYPE('archive', 'EMPTY')
199 if Options.options.with_libarchive is not False:
200 Logs.info("Checking for libarchive existence")
201 if conf.CHECK_HEADERS('archive.h') and conf.CHECK_LIB('archive', shlib=True):
202 conf.CHECK_FUNCS_IN('archive_read_support_filter_all archive_read_free', 'archive')
203 else:
204 conf.fatal("libarchive support not found. "
205 "Try installing libarchive-dev or libarchive-devel. "
206 "Otherwise, use --without-libarchive to "
207 "build without libarchive support. "
208 "libarchive support is required for the smbclient "
209 "tar-file mode")
210 elif conf.CONFIG_GET('ENABLE_SELFTEST'):
211 raise Errors.WafError('libarchive library required for '
212 '--enable-selftest')
215 # check for DMAPI libs
216 if Options.options.with_dmapi == False:
217 have_dmapi = False
218 else:
219 have_dmapi = True
220 Logs.info("Checking for DMAPI library existence")
221 samba_dmapi_lib = ''
222 if conf.CHECK_FUNCS_IN('dm_get_eventlist', 'dm'):
223 samba_dmapi_lib = 'dm'
224 else:
225 if conf.CHECK_FUNCS_IN('dm_get_eventlist', 'jfsdm'):
226 samba_dmapi_lib = 'jfsdm'
227 else:
228 if conf.CHECK_FUNCS_IN('dm_get_eventlist', 'dmapi'):
229 samba_dmapi_lib = 'dmapi'
230 else:
231 if conf.CHECK_FUNCS_IN('dm_get_eventlist', 'xdsm'):
232 samba_dmapi_lib = 'xdsm'
233 # only bother to test headers and compilation when a candidate
234 # library has been found
235 if samba_dmapi_lib == '':
236 have_dmapi = False
237 broken_dmapi = "no suitable DMAPI library found"
239 if have_dmapi:
240 conf.CHECK_HEADERS('sys/dmi.h xfs/dmapi.h sys/jfsdmapi.h sys/dmapi.h dmapi.h')
241 conf.CHECK_CODE('''
242 #include <time.h> /* needed by Tru64 */
243 #include <sys/types.h> /* needed by AIX */
244 #ifdef HAVE_XFS_DMAPI_H
245 #include <xfs/dmapi.h>
246 #elif defined(HAVE_SYS_DMI_H)
247 #include <sys/dmi.h>
248 #elif defined(HAVE_SYS_JFSDMAPI_H)
249 #include <sys/jfsdmapi.h>
250 #elif defined(HAVE_SYS_DMAPI_H)
251 #include <sys/dmapi.h>
252 #elif defined(HAVE_DMAPI_H)
253 #include <dmapi.h>
254 #endif
256 /* This link test is designed to fail on IRI 6.4, but should
257 * succeed on Linux, IRIX 6.5 and AIX.
259 int main(int argc, char **argv)
261 char * version;
262 dm_eventset_t events;
263 /* This doesn't take an argument on IRIX 6.4. */
264 dm_init_service(&version);
265 /* IRIX 6.4 expects events to be a pointer. */
266 DMEV_ISSET(DM_EVENT_READ, events);
268 return 0;
270 ''',
271 'USEABLE_DMAPI_LIBRARY',
272 addmain=False,
273 execute=False,
274 lib=samba_dmapi_lib,
275 msg='Checking whether DMAPI lib '+samba_dmapi_lib+' can be used')
276 if not conf.CONFIG_SET('USEABLE_DMAPI_LIBRARY'):
277 have_dmapi = False
278 broken_dmapi = "no usable DMAPI library found"
280 if have_dmapi:
281 Logs.info("Building with DMAPI support.")
282 conf.env['dmapi_lib'] = samba_dmapi_lib
283 conf.DEFINE('USE_DMAPI', 1)
284 else:
285 if Options.options.with_dmapi == False:
286 Logs.info("Building without DMAPI support (--without-dmapi).")
287 elif Options.options.with_dmapi == True:
288 Logs.error("DMAPI support not available: " + broken_dmapi)
289 conf.fatal('DMAPI support requested but not found.');
290 else:
291 Logs.warn("Building without DMAPI support: " + broken_dmapi)
292 conf.env['dmapi_lib'] = ''
294 # Check for various members of the stat structure
295 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_blocks', define='HAVE_STAT_ST_BLOCKS',
296 headers='sys/stat.h')
297 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_blksize', define='HAVE_STAT_ST_BLKSIZE',
298 headers='sys/stat.h')
299 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_flags', define='HAVE_STAT_ST_FLAGS',
300 headers='sys/types.h sys/stat.h unistd.h')
302 if conf.env.HAVE_BLKCNT_T:
303 conf.CHECK_CODE('''
304 static int test_array[1 - 2 * !(((long int)(sizeof(blkcnt_t))) <= 4)];''',
305 'SIZEOF_BLKCNT_T_4',
306 headers='replace.h sys/types.h sys/stat.h unistd.h',
307 msg="Checking whether blkcnt_t is 32 bit")
309 # If sizeof is 4 it can't be 8
310 if conf.env.HAVE_BLKCNT_T:
311 if not conf.CONFIG_SET('SIZEOF_BLKCNT_T_4'):
312 conf.CHECK_CODE('''
313 static int test_array[1 - 2 * !(((long int)(sizeof(blkcnt_t))) <= 8)];''',
314 'SIZEOF_BLKCNT_T_8',
315 headers='replace.h sys/types.h sys/stat.h unistd.h',
316 msg="Checking whether blkcnt_t is 64 bit")
318 # Check for POSIX capability support
319 conf.CHECK_FUNCS_IN('cap_get_proc', 'cap', headers='sys/capability.h')
321 if conf.env.HAVE_SYS_CAPABILITY_H:
322 conf.CHECK_CODE('''
323 cap_t cap;
324 cap_value_t vals[1];
325 if (!(cap = cap_get_proc())) exit(1);
326 vals[0] = CAP_CHOWN;
327 cap_set_flag(cap, CAP_INHERITABLE, 1, vals, CAP_CLEAR);
328 cap_set_proc(cap);''',
329 'HAVE_POSIX_CAPABILITIES', execute=True, lib="cap",
330 headers='sys/capability.h',
331 msg="Checking whether POSIX capabilities are available")
333 conf.CHECK_CODE('int i;', 'BROKEN_NISPLUS_INCLUDE_FILES',
334 headers='sys/types.h sys/acl.h rpcsvc/nis.h',
335 msg="Checking for broken nisplus include files")
337 # Check if the compiler will optimize out functions
338 conf.CHECK_CODE('''
339 #include <sys/types.h>
340 size_t __unsafe_string_function_usage_here_size_t__(void);
341 #define CHECK_STRING_SIZE(d, len) (sizeof(d) != (len) && sizeof(d) != sizeof(char *))
342 static size_t push_string_check_fn(void *dest, const char *src, size_t dest_len) {
343 return 0;
346 #define push_string_check(dest, src, dest_len) \
347 (CHECK_STRING_SIZE(dest, dest_len) \
348 ? __unsafe_string_function_usage_here_size_t__() \
349 : push_string_check_fn(dest, src, dest_len))
351 int main(int argc, char **argv) {
352 char outbuf[1024];
353 char *p = outbuf;
354 const char *foo = "bar";
355 p += 31 + push_string_check(p + 31, foo, sizeof(outbuf) - (p + 31 - outbuf));
356 return 0;
357 }''', 'HAVE_COMPILER_WILL_OPTIMIZE_OUT_FNS',
358 addmain=False,
359 add_headers=False,
360 msg="Checking if the compiler will optimize out functions")
362 # Check if the compiler supports the LL suffix on long long integers
363 # AIX needs this
364 conf.CHECK_CODE('long long i = 0x8000000000LL', 'COMPILER_SUPPORTS_LL',
365 headers='stdio.h',
366 msg="Checking for LL suffix on long long integers")
368 conf.CHECK_FUNCS('''
369 DNSServiceRegister
370 atexit
371 chflags
372 fchflags
373 chmod
374 crypt16
375 devnm
376 endmntent
377 execl
378 fchmod
379 fchown
380 fseeko
381 fsync
382 futimens
383 getauthuid
384 getcwd
385 getgrent
386 getgrnam
387 getgrouplist
388 getgrset
389 getmntent
390 getpagesize
391 getpwanam
392 getpwent_r
393 getrlimit
394 glob
395 grantpt
396 hstrerror
397 initgroups
398 innetgr
399 llseek
400 lutimes
401 memalign
402 mknod
403 mlock
404 mlockall
405 munlock
406 munlockall
407 pathconf poll
408 posix_memalign
409 pread
410 pwrite
411 rdchk
412 select
413 setenv
414 setgidx
415 setgroups
416 setlocale
417 setluid
418 setmntent
419 setpgid
420 setpriv
421 setsid
422 setuidx
423 statvfs
424 strcasecmp
425 strchr
426 strpbrk
427 strsignal
428 strtol
429 strupr
430 sysconf
431 sysctl
432 sysctlbyname
433 syslog
434 timegm
435 utimensat
436 vsyslog
437 ''')
439 conf.CHECK_SAMBA3_CHARSET() # see build/charset.py
441 # FIXME: these should be tests for features, but the old build system just
442 # checks for OSes.
443 host_os = sys.platform
444 Logs.info("building on %s" % host_os)
446 # Python doesn't have case switches... :/
447 # FIXME: original was *linux* | gnu* | k*bsd*-gnu | kopensolaris*-gnu | *qnx*)
448 # the search for .rfind('gnu') covers gnu* and *-gnu is that too broad?
450 conf.SET_TARGET_TYPE('sunacl', 'EMPTY')
451 if (host_os.rfind('linux') > -1) or (host_os.rfind('gnu') > -1) or (host_os.rfind('qnx') > -1):
452 if host_os.rfind('linux') > -1:
453 conf.DEFINE('LINUX', '1')
454 elif host_os.rfind('qnx') > -1:
455 conf.DEFINE('QNX', '1')
456 conf.DEFINE('STAT_ST_BLOCKSIZE', '512')
457 elif (host_os.rfind('darwin') > -1):
458 conf.DEFINE('DARWINOS', 1)
459 conf.ADD_CFLAGS('-fno-common')
460 conf.DEFINE('STAT_ST_BLOCKSIZE', '512')
461 elif (host_os.rfind('freebsd') > -1):
462 conf.DEFINE('FREEBSD', 1)
463 if conf.CHECK_HEADERS('sunacl.h'):
464 conf.DEFINE('HAVE_FREEBSD_SUNACL_H', '1')
465 conf.CHECK_FUNCS_IN(['acl'], 'sunacl')
466 conf.DEFINE('STAT_ST_BLOCKSIZE', '512')
467 elif (host_os.rfind('irix') > -1):
468 conf.DEFINE('IRIX', 1)
469 conf.DEFINE('STAT_ST_BLOCKSIZE', '512')
470 elif (host_os.rfind('aix') > -1):
471 conf.DEFINE('AIX', 1)
472 conf.DEFINE('STAT_ST_BLOCKSIZE', 'DEV_BSIZE')
473 elif (host_os.rfind('hpux') > -1):
474 conf.DEFINE('HPUX', 1)
475 conf.DEFINE('STAT_ST_BLOCKSIZE', '8192')
476 elif (host_os.rfind('osf') > -1):
477 conf.DEFINE('OSF1', 1)
478 conf.DEFINE('STAT_ST_BLOCKSIZE', '512')
480 # FIXME: Add more checks here.
481 else:
482 conf.DEFINE('STAT_ST_BLOCKSIZE', '512')
484 if Options.options.with_acl_support:
485 if (host_os.rfind('hpux') > -1):
486 Logs.info('Using HPUX ACLs')
487 conf.DEFINE('HAVE_HPUX_ACLS',1)
488 conf.DEFINE('POSIX_ACL_NEEDS_MASK',1)
489 required_static_modules.extend(['vfs_hpuxacl'])
490 elif (host_os.rfind('aix') > -1):
491 Logs.info('Using AIX ACLs')
492 conf.DEFINE('HAVE_AIX_ACLS',1)
493 required_static_modules.extend(['vfs_aixacl', 'vfs_aixacl2'])
494 elif (host_os.rfind('darwin') > -1):
495 Logs.warn('ACLs on Darwin currently not supported')
496 conf.fatal("ACL support not available on Darwin/MacOS. "
497 "Use --without-acl-support for building without "
498 "ACL support. "
499 "ACL support is required to change permissions "
500 "from Windows clients.")
501 else:
502 conf.CHECK_FUNCS_IN(['acl_get_file'], 'acl')
503 if conf.CHECK_CODE('''
504 acl_t acl;
505 int entry_id;
506 acl_entry_t *entry_p;
507 return acl_get_entry(acl, entry_id, entry_p);
508 ''',
509 'HAVE_POSIX_ACLS',
510 headers='sys/types.h sys/acl.h', link=False,
511 msg="Checking for POSIX ACL support") :
512 conf.CHECK_CODE('''
513 acl_permset_t permset_d;
514 acl_perm_t perm;
515 return acl_get_perm_np(permset_d, perm);
516 ''',
517 'HAVE_ACL_GET_PERM_NP',
518 headers='sys/types.h sys/acl.h', link=True,
519 msg="Checking whether acl_get_perm_np() is available")
520 # source3/lib/sysacls.c calls posixacl_sys_acl_get_file()
521 required_static_modules.extend(['vfs_posixacl'])
522 conf.CHECK_VARIABLE('ACL_EVERYONE', headers='sys/acl.h')
523 elif conf.CHECK_FUNCS_IN(['facl'], 'sec'):
524 Logs.info('Using solaris or UnixWare ACLs')
525 conf.DEFINE('HAVE_SOLARIS_UNIXWARE_ACLS',1)
526 required_static_modules.extend(['vfs_solarisacl'])
527 else:
528 conf.fatal("ACL support not found. Try installing libacl1-dev "
529 "or libacl-devel. "
530 "Otherwise, use --without-acl-support to build "
531 "without ACL support. "
532 "ACL support is required to change permissions from "
533 "Windows clients.")
535 if conf.CHECK_FUNCS('dirfd'):
536 conf.DEFINE('HAVE_DIRFD_DECL', 1)
538 conf.CHECK_CODE('struct statfs fsd; fsid_t fsid = fsd.f_fsid; return statfs(".", &fsd);',
539 'HAVE_STATFS_F_FSID',
540 msg="vfs_fileid checking for statfs() and struct statfs.f_fsid",
541 headers='sys/types.h sys/statfs.h',
542 execute=True)
544 if conf.CONFIG_SET('HAVE_FALLOCATE'):
545 conf.CHECK_CODE('''
546 int ret = fallocate(0, FALLOC_FL_KEEP_SIZE, 0, 10);''',
547 'HAVE_LINUX_FALLOCATE',
548 msg="Checking whether the Linux 'fallocate' function is available",
549 headers='unistd.h sys/types.h fcntl.h linux/falloc.h')
550 conf.CHECK_CODE('''
551 int ret = fallocate(0, FALLOC_FL_PUNCH_HOLE, 0, 10);''',
552 'HAVE_FALLOC_FL_PUNCH_HOLE',
553 msg="Checking whether Linux 'fallocate' supports hole-punching",
554 headers='unistd.h sys/types.h fcntl.h linux/falloc.h')
556 conf.CHECK_CODE('''
557 int ret = lseek(0, 0, SEEK_HOLE);
558 ret = lseek(0, 0, SEEK_DATA);''',
559 'HAVE_LSEEK_HOLE_DATA',
560 msg="Checking whether lseek supports hole/data seeking",
561 headers='unistd.h sys/types.h')
563 conf.CHECK_CODE('''
564 ssize_t err = readahead(0,0,0x80000);''',
565 'HAVE_LINUX_READAHEAD',
566 msg="Checking whether Linux readahead is available",
567 headers='unistd.h fcntl.h')
568 conf.CHECK_DECLS('readahead', headers='fcntl.h', always=True)
570 conf.CHECK_CODE('int fd = openat(AT_FDCWD, ".", O_RDONLY);',
571 'HAVE_OPENAT',
572 msg='Checking for openat',
573 headers='fcntl.h')
575 conf.CHECK_CODE('''
576 struct msghdr msg;
577 union {
578 struct cmsghdr cm;
579 char control[CMSG_SPACE(sizeof(int))];
580 } control_un;
581 msg.msg_control = control_un.control;
582 msg.msg_controllen = sizeof(control_un.control);
583 ''',
584 'HAVE_STRUCT_MSGHDR_MSG_CONTROL',
585 msg='Checking if we can use msg_control for passing file descriptors',
586 headers='sys/types.h stdlib.h stddef.h sys/socket.h sys/un.h')
587 conf.CHECK_CODE('''
588 struct msghdr msg;
589 int fd;
590 msg.msg_accrights = (caddr_t) &fd;
591 msg.msg_accrightslen = sizeof(fd);
592 ''',
593 'HAVE_STRUCT_MSGHDR_MSG_ACCRIGHTS',
594 msg='Checking if we can use msg_accrights for passing file descriptors',
595 headers='sys/types.h stdlib.h stddef.h sys/socket.h sys/un.h')
597 if Options.options.with_winbind:
598 conf.env.build_winbind = True
599 conf.DEFINE('WITH_WINBIND', '1')
601 conf.find_program('awk', var='AWK')
603 conf.CHECK_HEADERS('asm/types.h')
605 conf.CHECK_CODE('dev_t dev; int i = major(dev); return 0', "HAVE_DEVICE_MAJOR_FN",
606 headers='unistd.h sys/types.h',
607 msg="Checking for major macro")
609 conf.CHECK_CODE('dev_t dev; int i = minor(dev); return 0', "HAVE_DEVICE_MINOR_FN",
610 headers='unistd.h sys/types.h',
611 msg="Checking for minor macro")
613 conf.CHECK_STRUCTURE_MEMBER('struct dirent', 'd_off',
614 headers='unistd.h sys/types.h dirent.h',
615 define='HAVE_DIRENT_D_OFF')
617 if (conf.CONFIG_SET('HAVE_GETDOMAINNAME')):
618 conf.DEFINE('HAVE_NETGROUP', '1')
620 # Look for CUPS
621 if Options.options.with_cups:
622 conf.find_program('cups-config', var='CUPS_CONFIG')
623 if conf.env.CUPS_CONFIG:
624 # we would normally use --libs here, but cups-config incorrectly adds
625 # gssapi_krb5 and other libraries to its --libs output. That breaks the use
626 # of an in-tree heimdal kerberos
627 conf.CHECK_CFG(path=conf.env.CUPS_CONFIG, args="--cflags --ldflags",
628 package="", uselib_store="CUPS")
629 conf.CHECK_HEADERS('cups/cups.h cups/language.h', lib='cups')
630 conf.CHECK_FUNCS_IN('httpConnect httpConnect2 httpConnectEncrypt', 'cups')
631 if conf.CONFIG_SET('HAVE_CUPS_CUPS_H') and conf.CONFIG_SET('HAVE_CUPS_LANGUAGE_H'):
632 conf.DEFINE('HAVE_CUPS', '1')
633 else:
634 conf.undefine('HAVE_CUPS')
635 conf.SET_TARGET_TYPE('cups', 'EMPTY')
636 else:
637 # define an empty subsystem for cups, to allow it to be used as an empty dependency
638 conf.SET_TARGET_TYPE('cups', 'EMPTY')
640 if Options.options.with_iprint:
641 if conf.CONFIG_SET('HAVE_CUPS'):
642 conf.DEFINE('HAVE_IPRINT', '1')
643 else:
644 Logs.warn("--enable-iprint=yes but cups support not sufficient")
645 if Options.options.with_syslog:
646 conf.DEFINE('WITH_SYSLOG', '1')
647 if Options.options.with_automount:
648 conf.DEFINE('WITH_AUTOMOUNT', '1')
650 # Check for LDAP
651 if Options.options.with_ldap:
652 conf.CHECK_HEADERS('ldap.h lber.h ldap_pvt.h')
653 conf.CHECK_TYPE('ber_tag_t', 'unsigned int', headers='ldap.h lber.h')
654 conf.CHECK_FUNCS_IN('ber_scanf ber_sockbuf_add_io', 'lber')
655 conf.CHECK_VARIABLE('LDAP_OPT_SOCKBUF', headers='ldap.h')
657 # if we LBER_OPT_LOG_PRINT_FN we can intercept ldap logging and print it out
658 # for the samba logs
659 conf.CHECK_VARIABLE('LBER_OPT_LOG_PRINT_FN',
660 define='HAVE_LBER_LOG_PRINT_FN', headers='lber.h')
662 conf.CHECK_FUNCS_IN('ldap_init ldap_init_fd ldap_initialize ldap_set_rebind_proc', 'ldap')
663 conf.CHECK_FUNCS_IN('ldap_add_result_entry', 'ldap')
665 # Check if ldap_set_rebind_proc() takes three arguments
666 if conf.CHECK_CODE('ldap_set_rebind_proc(0, 0, 0)',
667 'LDAP_SET_REBIND_PROC_ARGS',
668 msg="Checking whether ldap_set_rebind_proc takes 3 arguments",
669 headers='ldap.h lber.h', link=False):
670 conf.DEFINE('LDAP_SET_REBIND_PROC_ARGS', '3')
671 else:
672 conf.DEFINE('LDAP_SET_REBIND_PROC_ARGS', '2')
674 # last but not least, if ldap_init() exists, we want to use ldap
675 if conf.CONFIG_SET('HAVE_LDAP_INIT') and conf.CONFIG_SET('HAVE_LDAP_H'):
676 conf.DEFINE('HAVE_LDAP', '1')
677 conf.DEFINE('LDAP_DEPRECATED', '1')
678 conf.env['HAVE_LDAP'] = '1'
679 # if ber_sockbuf_add_io() and LDAP_OPT_SOCKBUF are available, we can add
680 # SASL wrapping hooks
681 if conf.CONFIG_SET('HAVE_BER_SOCKBUF_ADD_IO') and \
682 conf.CONFIG_SET('HAVE_LDAP_OPT_SOCKBUF'):
683 conf.DEFINE('HAVE_LDAP_SASL_WRAPPING', '1')
684 else:
685 conf.fatal("LDAP support not found. "
686 "Try installing libldap2-dev or openldap-devel. "
687 "Otherwise, use --without-ldap to build without "
688 "LDAP support. "
689 "LDAP support is required for the LDAP passdb backend, "
690 "LDAP idmap backends and ADS. "
691 "ADS support improves communication with "
692 "Active Directory domain controllers.")
693 else:
694 conf.SET_TARGET_TYPE('ldap', 'EMPTY')
695 conf.SET_TARGET_TYPE('lber', 'EMPTY')
697 if Options.options.with_ads == False:
698 use_ads = False
699 use_ads_krb5 = False
700 use_ads_ldap = False
701 else:
702 use_ads = True
703 use_ads_krb5 = True
704 use_ads_ldap = True
705 if not conf.CONFIG_SET('HAVE_ENCTYPE_ARCFOUR_HMAC_MD5') and \
706 not conf.CONFIG_SET('HAVE_ENCTYPE_ARCFOUR_HMAC'):
707 Logs.warn("arcfour-hmac-md5 encryption type not found in -lkrb5")
708 use_ads_krb5 = False
709 if not conf.CONFIG_SET('HAVE_KRB5_MK_REQ_EXTENDED'):
710 Logs.warn("krb5_mk_req_extended not found in -lkrb5")
711 use_ads_krb5 = False
712 if not conf.CONFIG_SET('HAVE_KRB5_GET_HOST_REALM'):
713 Logs.warn("krb5_get_host_realm not found in -lkrb5")
714 use_ads_krb5 = False
715 if not conf.CONFIG_SET('HAVE_KRB5_FREE_HOST_REALM'):
716 Logs.warn("krb5_free_host_realm not found in -lkrb5")
717 use_ads_krb5 = False
718 if not conf.CONFIG_SET('HAVE_KRB5_FWD_TGT_CREDS'):
719 Logs.warn("krb5_fwd_tgt_creds found in -lkrb5")
720 use_ads_krb5 = False
721 if not conf.CONFIG_SET('HAVE_KRB5_GET_INIT_CREDS_OPT_ALLOC'):
722 Logs.warn("krb5_get_init_creds_opt_alloc not found in -lkrb5")
723 use_ads_krb5 = False
724 if not conf.CONFIG_SET('KRB5_CREDS_OPT_FREE_REQUIRES_CONTEXT'):
725 Logs.warn("krb5_get_init_creds_opt_free was not found or was too old in -lkrb5")
726 use_ads_krb5 = False
727 if not conf.CONFIG_SET('HAVE_KRB5_GET_RENEWED_CREDS'):
728 Logs.warn("krb5_get_renewed_creds not found in -lkrb5")
729 use_ads_krb5 = False
730 if not conf.CONFIG_SET('HAVE_KRB5_PRINCIPAL_COMPARE_ANY_REALM'):
731 Logs.warn("krb5_principal_compare_any_realm not found in -lkrb5")
732 use_ads_krb5 = False
733 if not conf.CONFIG_SET('HAVE_KRB5_C_STRING_TO_KEY') and \
734 not conf.CONFIG_SET('HAVE_KRB5_STRING_TO_KEY_SALT'):
735 Logs.warn("krb5_c_string_to_key not found in -lkrb5")
736 use_ads_krb5 = False
737 if not conf.CONFIG_SET('HAVE_KRB5_PRINCIPAL2SALT') and \
738 not conf.CONFIG_SET('HAVE_KRB5_GET_PW_SALT'):
739 Logs.warn("no CREATE_KEY_FUNCTIONS detected")
740 use_ads_krb5 = False
741 if not conf.CONFIG_SET('HAVE_KRB5_GET_PERMITTED_ENCTYPES') and \
742 not conf.CONFIG_SET('HAVE_KRB5_GET_DEFAULT_IN_TKT_ETYPES'):
743 Logs.warn("no GET_ENCTYPES_FUNCTIONS detected")
744 use_ads_krb5 = False
745 if not conf.CONFIG_SET('HAVE_KRB5_KT_FREE_ENTRY') and \
746 not conf.CONFIG_SET('HAVE_KRB5_FREE_KEYTAB_ENTRY_CONTENTS'):
747 Logs.warn("no KT_FREE_FUNCTION detected")
748 use_ads_krb5 = False
749 if not conf.CONFIG_SET('HAVE_KRB5_C_VERIFY_CHECKSUM'):
750 Logs.warn("krb5_c_verify_checksum_compare not found in -lkrb5")
751 use_ads_krb5 = False
753 # We don't actually use
754 # gsskrb5_extract_authz_data_from_sec_context, but it is a
755 # clue that this Heimdal, which does the PAC processing we
756 # need on the standard gss_inquire_sec_context_by_oid
757 if not conf.CONFIG_SET('HAVE_GSS_GET_NAME_ATTRIBUTE') and \
758 not (conf.CONFIG_SET('HAVE_GSSKRB5_EXTRACT_AUTHZ_DATA_FROM_SEC_CONTEXT') and \
759 conf.CONFIG_SET('HAVE_GSS_INQUIRE_SEC_CONTEXT_BY_OID')):
760 Logs.warn("need either gss_get_name_attribute or gsskrb5_extract_authz_data_from_sec_context and gss_inquire_sec_context_by_oid in -lgssapi for PAC support")
761 use_ads_krb5 = False
763 if not conf.CONFIG_SET('HAVE_GSS_KRB5_EXPORT_LUCID_SEC_CONTEXT'):
764 Logs.warn("need gss_krb5_export_lucid_sec_context for SPNEGO and gss_wrap support")
765 use_ads_krb5 = False
767 if use_ads_krb5:
768 conf.DEFINE('HAVE_KRB5', '1')
769 conf.env['HAVE_KRB5'] = '1'
770 else:
771 conf.undefine('HAVE_KRB5_H')
772 conf.undefine('HAVE_GSSAPI_H')
773 conf.undefine('HAVE_GSSAPI_GSSAPI_GENERIC_H')
774 conf.undefine('HAVE_GSSAPI_GSSAPI_H')
775 use_ads = False
777 if not conf.CONFIG_SET('HAVE_LDAP'):
778 use_ads = False
779 use_ads_ldap = False
781 if use_ads:
782 conf.DEFINE('WITH_ADS', '1')
783 conf.env['HAVE_ADS'] = '1'
784 Logs.info("Building with Active Directory support.")
785 # these have broken dependencies
786 forced_shared_modules.extend(['idmap_ad', 'idmap_rfc2307'])
787 elif Options.options.with_ads == False:
788 Logs.info("Building without Active Directory support (--without-ads).")
789 if not Options.options.without_ad_dc:
790 conf.fatal("Building --without-ads requires also "
791 "building --without-ad-dc.")
792 else:
793 if not use_ads_krb5:
794 Logs.warn("Active Directory support not available: krb5 libs don't have all required features")
795 if not use_ads_ldap:
796 Logs.warn("Active Directory support not available: LDAP support is not available.")
797 if Options.options.with_ads:
798 conf.fatal("Active Directory support not found. Use --without-ads "
799 "for building without Active Directory support. "
800 "ADS support improves communication with "
801 "Active Directory domain controllers.")
802 else:
803 # this is the auto-mode case
804 Logs.warn("Building without Active Directory support.")
807 if Options.options.with_utmp:
808 conf.env.with_utmp = True
809 if not conf.CHECK_HEADERS('utmp.h'): conf.env.with_utmp = False
810 conf.CHECK_FUNCS('pututline pututxline updwtmp updwtmpx getutmpx getutxent')
811 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_name', headers='utmp.h',
812 define='HAVE_UT_UT_NAME')
813 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_user', headers='utmp.h',
814 define='HAVE_UT_UT_USER')
815 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_id', headers='utmp.h',
816 define='HAVE_UT_UT_ID')
817 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_host', headers='utmp.h',
818 define='HAVE_UT_UT_HOST')
819 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_time', headers='utmp.h',
820 define='HAVE_UT_UT_TIME')
821 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_tv', headers='utmp.h',
822 define='HAVE_UT_UT_TV')
823 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_type', headers='utmp.h',
824 define='HAVE_UT_UT_TYPE')
825 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_pid', headers='utmp.h',
826 define='HAVE_UT_UT_PID')
827 conf.CHECK_STRUCTURE_MEMBER('struct utmp', 'ut_exit.e_exit', headers='utmp.h',
828 define='HAVE_UT_UT_EXIT')
829 conf.CHECK_STRUCTURE_MEMBER('struct utmpx', 'ut_syslen', headers='utmpx.h',
830 define='HAVE_UX_UT_SYSLEN')
831 conf.CHECK_STRUCTURE_MEMBER('struct utmpx', 'ut_host', headers='utmpx.h',
832 define='HAVE_UX_UT_HOST')
833 conf.CHECK_CODE('struct utmp utarg; struct utmp *utreturn; utreturn = pututline(&utarg);',
834 'PUTUTLINE_RETURNS_UTMP', headers='utmp.h',
835 msg="Checking whether pututline returns pointer")
836 conf.CHECK_SIZEOF(['((struct utmp *)NULL)->ut_line'], headers='utmp.h',
837 define='SIZEOF_UTMP_UT_LINE', critical=False)
838 if not conf.CONFIG_SET('SIZEOF_UTMP_UT_LINE'):
839 conf.env.with_utmp = False
840 elif int(conf.env.SIZEOF_UTMP_UT_LINE) < 15:
841 conf.env.with_utmp = False
842 if conf.env.with_utmp:
843 conf.DEFINE('WITH_UTMP', 1)
844 else:
845 Logs.warn("--with-utmp but utmp support not sufficient")
847 if Options.options.with_avahi:
848 conf.env.with_avahi = True
849 if not conf.CHECK_HEADERS('avahi-common/watch.h avahi-client/client.h'): conf.env.with_avahi = False
850 if not conf.CHECK_FUNCS_IN('avahi_client_new', 'avahi-client'): conf.env.with_avahi = False
851 if not conf.CHECK_FUNCS_IN('avahi_strerror', 'avahi-common'): conf.env.with_avahi = False
852 if conf.env.with_avahi:
853 conf.DEFINE('WITH_AVAHI_SUPPORT', 1)
854 else:
855 conf.SET_TARGET_TYPE('avahi-common', 'EMPTY')
856 conf.SET_TARGET_TYPE('avahi-client', 'EMPTY')
858 if Options.options.with_iconv:
859 conf.env.with_iconv = True
860 if not conf.CHECK_FUNCS_IN('iconv_open', 'iconv', headers='iconv.h'):
861 conf.env.with_iconv = False
862 if conf.env.with_iconv:
863 conf.DEFINE('HAVE_ICONV', 1)
865 if Options.options.with_pam:
866 use_pam=True
867 conf.CHECK_HEADERS('security/pam_appl.h pam/pam_appl.h')
868 if not conf.CONFIG_SET('HAVE_SECURITY_PAM_APPL_H') and not conf.CONFIG_SET('HAVE_PAM_PAM_APPL_H'):
869 Logs.warn("--with-pam=yes but pam_appl.h not found")
870 use_pam=False
871 conf.CHECK_FUNCS_IN('pam_get_data', 'pam')
872 conf.CHECK_HEADERS('security/pam_modules.h pam/pam_modules.h')
873 if not conf.CONFIG_SET('HAVE_SECURITY_PAM_MODULES_H') and not conf.CONFIG_SET('HAVE_PAM_PAM_MODULES_H'):
874 Logs.warn("--with-pam=yes but pam_modules.h not found")
875 use_pam=False
876 conf.CHECK_HEADERS('security/pam_ext.h security/_pam_macros.h')
877 conf.CHECK_HEADERS('pam/pam_ext.h pam/_pam_macros.h')
878 conf.CHECK_FUNCS_IN('pam_vsyslog', 'pam')
879 conf.CHECK_CODE('''
880 #if defined(HAVE_SECURITY_PAM_APPL_H)
881 #include <security/pam_appl.h>
882 #elif defined(HAVE_PAM_PAM_APPL_H)
883 #include <pam/pam_appl.h>
884 #endif
885 pam_set_item(0, PAM_RHOST, 0);
886 ''',
887 'HAVE_PAM_RHOST',
888 lib='pam',
889 msg="Checking whether PAM_RHOST is available");
890 conf.CHECK_CODE('''
891 #if defined(HAVE_SECURITY_PAM_APPL_H)
892 #include <security/pam_appl.h>
893 #elif defined(HAVE_PAM_PAM_APPL_H)
894 #include <pam/pam_appl.h>
895 #endif
896 pam_set_item(0, PAM_TTY, 0);
897 ''',
898 'HAVE_PAM_TTY',
899 lib='pam',
900 msg="Checking whether PAM_TTY is available");
901 conf.CHECK_CODE('''
902 #if (!defined(LINUX))
904 #define PAM_EXTERN extern
905 #if defined(HAVE_SECURITY_PAM_APPL_H)
906 #include <security/pam_appl.h>
907 #elif defined(HAVE_PAM_PAM_APPL_H)
908 #include <pam/pam_appl.h>
909 #endif
911 #endif
913 #if defined(HAVE_SECURITY_PAM_MODULES_H)
914 #include <security/pam_modules.h>
915 #elif defined(HAVE_PAM_PAM_MODULES_H)
916 #include <pam/pam_modules.h>
917 #endif
919 #if defined(HAVE_SECURITY__PAM_MACROS_H)
920 #include <security/_pam_macros.h>
921 #elif defined(HAVE_PAM__PAM_MACROS_H)
922 #include <pam/_pam_macros.h>
923 #endif
925 #ifdef HAVE_SECURITY_PAM_EXT_H
926 #include <security/pam_ext.h>
927 #endif
929 int i; i = PAM_RADIO_TYPE;
930 ''',
931 'HAVE_PAM_RADIO_TYPE',
932 lib='pam',
933 msg="Checking whether PAM_RADIO_TYPE is available");
934 if use_pam:
935 conf.DEFINE('WITH_PAM', 1)
936 conf.DEFINE('WITH_PAM_MODULES', 1)
937 else:
938 conf.fatal("PAM support is enabled but prerequisite libraries "
939 "or headers not found. Use --without-pam to disable "
940 "PAM support.");
942 seteuid = False
945 # Ensure we select the correct set of system calls on Linux.
947 if (host_os.rfind('linux') > -1):
948 conf.CHECK_CODE('''
949 #if defined(HAVE_UNISTD_H)
950 #include <unistd.h>
951 #endif
952 #include <stdlib.h>
953 #include <stdio.h>
954 #include <sys/types.h>
955 #include <errno.h>
957 #ifdef HAVE_SYS_PRIV_H
958 #include <sys/priv.h>
959 #endif
960 #ifdef HAVE_SYS_ID_H
961 #include <sys/id.h>
962 #endif
964 #if defined(HAVE_SYSCALL_H)
965 #include <syscall.h>
966 #endif
968 #if defined(HAVE_SYS_SYSCALL_H)
969 #include <sys/syscall.h>
970 #endif
972 syscall(SYS_setresuid32, -1, -1, -1);
973 syscall(SYS_setresgid32, -1, -1, -1);
974 syscall(SYS_setreuid32, -1, -1);
975 syscall(SYS_setregid32, -1, -1);
976 syscall(SYS_setuid32, -1);
977 syscall(SYS_setgid32, -1);
978 syscall(SYS_setgroups32, 0, NULL);
979 ''',
980 'USE_LINUX_32BIT_SYSCALLS',
981 msg="Checking whether Linux should use 32-bit credential calls");
983 if (conf.CONFIG_SET('USE_LINUX_32BIT_SYSCALLS')):
984 seteuid = conf.CHECK_CODE('''
985 #define AUTOCONF_TEST 1
986 #define HAVE_LINUX_THREAD_CREDENTIALS 1
987 #define USE_LINUX_32BIT_SYSCALLS 1
988 #include "../lib/util/setid.c"
989 #include "./lib/util_sec.c"
990 ''',
991 'HAVE_LINUX_THREAD_CREDENTIALS',
992 addmain=False,
993 execute=True,
994 msg="Checking whether we can use Linux thread-specific credentials with 32-bit system calls")
995 else:
996 seteuid = conf.CHECK_CODE('''
997 #define AUTOCONF_TEST 1
998 #define HAVE_LINUX_THREAD_CREDENTIALS 1
999 #include "../lib/util/setid.c"
1000 #include "./lib/util_sec.c"
1001 ''',
1002 'HAVE_LINUX_THREAD_CREDENTIALS',
1003 addmain=False,
1004 execute=True,
1005 msg="Checking whether we can use Linux thread-specific credentials")
1006 if not seteuid:
1007 seteuid = conf.CHECK_CODE('''
1008 #define AUTOCONF_TEST 1
1009 #define USE_SETREUID 1
1010 #include "../lib/util/setid.c"
1011 #include "./lib/util_sec.c"
1012 ''',
1013 'USE_SETREUID',
1014 addmain=False,
1015 execute=True,
1016 msg="Checking whether setreuid is available")
1017 if not seteuid:
1018 seteuid = conf.CHECK_CODE('''
1019 #define AUTOCONF_TEST 1
1020 #define USE_SETRESUID 1
1021 #include "../lib/util/setid.c"
1022 #include "./lib/util_sec.c"
1023 ''',
1024 'USE_SETRESUID',
1025 addmain=False,
1026 execute=True,
1027 msg="Checking whether setresuid is available")
1028 if not seteuid:
1029 seteuid = conf.CHECK_CODE('''
1030 #define AUTOCONF_TEST 1
1031 #define USE_SETEUID 1
1032 #include "../lib/util/setid.c"
1033 #include "./lib/util_sec.c"
1034 ''',
1035 'USE_SETEUID',
1036 addmain=False,
1037 execute=True,
1038 msg="Checking whether seteuid is available")
1039 if not seteuid:
1040 seteuid = conf.CHECK_CODE('''
1041 #define AUTOCONF_TEST 1
1042 #define USE_SETUIDX 1
1043 #include "../lib/util/setid.c"
1044 #include "./lib/util_sec.c"
1045 ''',
1046 'USE_SETUIDX',
1047 addmain=False,
1048 execute=True,
1049 mandatory=True,
1050 msg="Checking whether setuidx is available")
1051 # valgrind.h or valgrind/valgrind.h is checked in lib/replace/wscript
1052 if Options.options.developer:
1053 if conf.CONFIG_SET('HAVE_VALGRIND_H') or conf.CONFIG_SET('HAVE_VALGRIND_VALGRIND_H'):
1054 conf.DEFINE('VALGRIND', '1')
1056 if conf.CHECK_CODE('''
1057 #include <bits/sockaddr.h>
1058 #include <linux/netlink.h>
1059 ''',
1060 'HAVE_LINUX_NETLINK_H',
1061 msg="Checking whether Linux netlink is available"):
1063 conf.CHECK_CODE('''
1064 #include <bits/sockaddr.h>
1065 #include <linux/netlink.h>
1066 #include <linux/rtnetlink.h>
1067 ''',
1068 'HAVE_LINUX_RTNETLINK_H',
1069 msg='Checking whether Linux rtnetlink is available')
1071 conf.CHECK_CODE('''
1072 #include "../tests/fcntl_lock.c"
1073 ''',
1074 'HAVE_FCNTL_LOCK',
1075 addmain=False,
1076 execute=True,
1077 msg='Checking whether fcntl locking is available')
1079 conf.CHECK_CODE('''
1080 #include <unistd.h>
1081 #include <sys/types.h>
1082 #include <sys/stat.h>
1083 #include <fcntl.h>
1084 #include <errno.h>
1086 #define DATA "ofdtest.fcntl"
1088 int main() {
1089 struct flock lck = {
1090 .l_whence = SEEK_SET,
1091 .l_type = F_WRLCK,
1092 .l_start = 0,
1093 .l_len = 1,
1094 .l_pid = 0,
1096 int ret;
1097 int fd1;
1098 int fd2;
1099 char *testdir = getenv("TESTDIR");
1101 if (testdir) {
1102 if (chdir(testdir) != 0) {
1103 goto err;
1107 unlink(DATA);
1108 fd1 = open(DATA, O_RDWR|O_CREAT|O_EXCL, 0600);
1109 fd2 = open(DATA, O_RDWR);
1110 if (fd1 == -1 || fd2 == -1) {
1111 goto err;
1113 ret = fcntl(fd1,F_OFD_SETLKW,&lck);
1114 if (ret == -1) {
1115 goto err;
1117 ret = fcntl(fd2,F_OFD_SETLK,&lck);
1118 if (ret != -1) {
1119 goto err;
1121 if (errno != EAGAIN) {
1122 goto err;
1124 ret = fcntl(fd2,F_OFD_GETLK,&lck);
1125 if (ret == -1) {
1126 goto err;
1128 unlink(DATA);
1129 exit(0);
1130 err:
1131 unlink(DATA);
1132 exit(1);
1133 }''',
1134 'HAVE_OFD_LOCKS',
1135 addmain=False,
1136 execute=True,
1137 msg="Checking whether fcntl lock supports open file description locks")
1139 conf.CHECK_CODE('''
1140 #include <fcntl.h>
1141 #include <unistd.h>
1142 #include <stdlib.h>
1143 #include <sys/socket.h>
1145 int main(void)
1147 int sockfd, ret;
1148 struct f_owner_ex owner, get_owner;
1150 sockfd = socket(AF_UNIX, SOCK_STREAM, 0);
1151 if (sockfd == -1) {
1152 goto err;
1155 owner.type = F_OWNER_PID;
1156 owner.pid = getpid();
1158 ret = fcntl(sockfd, F_SETOWN_EX, &owner);
1159 if (ret == -1) {
1160 goto err;
1163 ret = fcntl(sockfd, F_GETOWN_EX, &get_owner);
1164 if (ret == -1) {
1165 goto err;
1168 if (get_owner.type != F_OWNER_PID) {
1169 goto err;
1172 if (get_owner.pid != getpid()) {
1173 goto err;
1176 close(sockfd);
1177 exit(0);
1178 err:
1179 close(sockfd);
1180 exit(1);
1181 }''',
1182 'HAVE_F_OWNER_EX',
1183 addmain=False,
1184 execute=True,
1185 msg="Checking whether fcntl supports flags to send direct I/O availability signals")
1187 conf.CHECK_CODE('''
1188 #include <fcntl.h>
1189 #include <unistd.h>
1190 #include <stdlib.h>
1191 #include <stdint.h>
1193 #define DATA "hinttest.fcntl"
1195 int main(void)
1197 uint64_t hint, get_hint;
1198 int fd;
1200 fd = open(DATA, O_RDONLY | O_CREAT | O_EXCL);
1201 if (fd == -1) {
1202 goto err;
1205 hint = RWH_WRITE_LIFE_SHORT;
1206 int ret = fcntl(fd, F_SET_RW_HINT, &hint);
1207 if (ret == -1) {
1208 goto err;
1211 ret = fcntl(fd, F_GET_RW_HINT, &get_hint);
1212 if (ret == -1) {
1213 goto err;
1216 if (get_hint != RWH_WRITE_LIFE_SHORT) {
1217 goto err;
1220 hint = RWH_WRITE_LIFE_EXTREME;
1221 ret = fcntl(fd, F_SET_FILE_RW_HINT, &hint);
1222 if (ret == -1) {
1223 goto err;
1226 ret = fcntl(fd, F_GET_FILE_RW_HINT, &get_hint);
1227 if (ret == -1) {
1228 goto err;
1231 if (get_hint != RWH_WRITE_LIFE_EXTREME) {
1232 goto err;
1235 close(fd);
1236 unlink(DATA);
1237 exit(0);
1238 err:
1239 close(fd);
1240 unlink(DATA);
1241 exit(1);
1242 }''',
1243 'HAVE_RW_HINTS',
1244 addmain=False,
1245 execute=True,
1246 msg="Checking whether fcntl supports setting/geting hints")
1248 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_mtim.tv_nsec',
1249 define='HAVE_STRUCT_STAT_ST_MTIM_TV_NSEC') # Linux, Solaris
1250 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_mtimensec',
1251 define='HAVE_STRUCT_STAT_ST_MTIMENSEC') # BSD, if defined _POSIX_SOURCE
1252 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_mtimespec.tv_nsec',
1253 define='HAVE_STRUCT_STAT_ST_MTIMESPEC_TV_NSEC') # BSD, if not defined _POSIX_SOURCE
1254 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_mtime_n',
1255 define='HAVE_STRUCT_STAT_ST_MTIME_N') # AIX
1256 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_umtime',
1257 define='HAVE_STRUCT_STAT_ST_UMTIME') # Tru64
1258 if conf.CONFIG_SET('HAVE_STRUCT_STAT_ST_MTIM_TV_NSEC') or \
1259 conf.CONFIG_SET('HAVE_STRUCT_STAT_ST_MTIMENSEC') or \
1260 conf.CONFIG_SET('HAVE_STRUCT_STAT_ST_MTIMESPEC_TV_NSEC') or \
1261 conf.CONFIG_SET('HAVE_STRUCT_STAT_ST_MTIME_N') or \
1262 conf.CONFIG_SET('HAVE_STRUCT_STAT_ST_UMTIME'):
1263 conf.DEFINE('HAVE_STAT_HIRES_TIMESTAMPS', '1')
1265 # recent FreeBSD, NetBSD have creation timestamps called birthtime:
1266 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_birthtime',
1267 define='HAVE_STRUCT_STAT_ST_BIRTHTIME')
1268 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_birthtimespec.tv_nsec',
1269 define='HAVE_STRUCT_STAT_ST_BIRTHTIMESPEC_TV_NSEC')
1270 conf.CHECK_STRUCTURE_MEMBER('struct stat', 'st_birthtimensec',
1271 define='HAVE_STRUCT_STAT_ST_BIRTHTIMENSEC')
1273 conf.CHECK_CODE('''
1274 ssize_t err = posix_fadvise(0,0,0x80000,POSIX_FADV_WILLNEED);
1275 ''',
1276 'HAVE_POSIX_FADVISE',
1277 msg='Checking whether posix_fadvise is available',
1278 headers='unistd.h fcntl.h')
1280 for v in ['_SC_NGROUPS_MAX', '_SC_NPROC_ONLN', '_SC_NPROCESSORS_ONLN', '_SC_PAGESIZE' ]:
1281 conf.CHECK_CODE('''
1282 #include <unistd.h>
1283 return sysconf(%s) == -1 ? 1 : 0;
1284 ''' % v,
1285 'SYSCONF%s' % v,
1286 msg='Checking whether sysconf(%s) is available' % v)
1288 conf.CHECK_CODE('''
1289 #include <sys/syscall.h>
1290 #include <unistd.h>
1291 syscall(SYS_initgroups, 16, NULL, NULL, 0);
1292 ''',
1293 'HAVE_DARWIN_INITGROUPS',
1294 msg='Checking whether to use the Darwin-specific initgroups system call')
1296 conf.CHECK_CODE('''struct utimbuf tbuf; tbuf.actime = 0; tbuf.modtime = 1; exit(utime("foo.c",&tbuf));''',
1297 'HAVE_UTIMBUF',
1298 headers='sys/types.h utime.h',
1299 msg='Checking whether struct utimbuf is available')
1301 if conf.CHECK_CODE('''struct sigevent s;''',
1302 'HAVE_STRUCT_SIGEVENT',
1303 headers='sys/types.h stdlib.h stddef.h signal.h',
1304 msg='Checking whether we have the struct sigevent'):
1305 conf.CHECK_STRUCTURE_MEMBER('struct sigevent', 'sigev_value.sival_ptr',
1306 define='HAVE_STRUCT_SIGEVENT_SIGEV_VALUE_SIVAL_PTR',
1307 headers='signal.h');
1308 conf.CHECK_STRUCTURE_MEMBER('struct sigevent', 'sigev_value.sigval_ptr',
1309 define='HAVE_STRUCT_SIGEVENT_SIGEV_VALUE_SIGVAL_PTR',
1310 headers='signal.h');
1312 if os.path.exists('/proc/sys/kernel/core_pattern'):
1313 conf.DEFINE('HAVE_SYS_KERNEL_PROC_CORE_PATTERN', '1')
1315 if conf.CHECK_CODE('''
1316 #include <time.h>
1317 main() {
1318 struct tm *tm;
1319 if (sizeof(time_t) == 8) {
1320 time_t max_time = 0x7fffffffffffffffll;
1321 tm = gmtime(&max_time);
1322 /* This should fail with 32-bit tm_year. */
1323 if (tm == NULL) {
1324 /* Max time_t that works with 32-bit int tm_year in struct tm. */
1325 max_time = 67768036191676799ll;
1326 tm = gmtime(&max_time);
1327 if (tm) {
1328 exit(0);
1332 exit(1);
1333 }''',
1334 '__TIME_T_MAX',
1335 addmain=False,
1336 execute=True,
1337 msg="Checking for the maximum value of the 'time_t' type"):
1338 conf.DEFINE('TIME_T_MAX', '67768036191676799ll')
1340 conf.CHECK_CODE('''
1341 #if defined(HAVE_UNISTD_H)
1342 #include <unistd.h>
1343 #endif
1344 #include <sys/types.h>
1345 #if defined(HAVE_SYS_SYSMACROS_H)
1346 #include <sys/sysmacros.h>
1347 #endif
1348 main() { dev_t dev = makedev(1,2); return 0; }
1349 ''',
1350 'HAVE_MAKEDEV',
1351 addmain=False,
1352 msg='Checking whether the macro for makedev is available')
1354 conf.CHECK_CODE('''
1355 #include <stdio.h>
1356 #include <limits.h>
1357 #include <signal.h>
1359 void exit_on_core(int ignored) {
1360 exit(1);
1363 main() {
1364 char *newpath;
1365 signal(SIGSEGV, exit_on_core);
1366 newpath = realpath("/tmp", NULL);
1367 exit((newpath != NULL) ? 0 : 1);
1369 ''',
1370 'REALPATH_TAKES_NULL',
1371 addmain=False,
1372 execute=True,
1373 msg='Checking whether the realpath function allows a NULL argument')
1375 conf.CHECK_CODE('''#include "../tests/ftruncate.c"''',
1376 'HAVE_FTRUNCATE_EXTEND',
1377 msg='Checking for ftruncate extend',
1378 addmain=False,
1379 execute=True)
1381 conf.CHECK_CODE('''#include "../tests/readlink.c"''',
1382 'HAVE_BROKEN_READLINK',
1383 msg='Checking for readlink breakage',
1384 addmain=False,
1385 execute=True)
1387 conf.SET_TARGET_TYPE('sendfile', 'EMPTY')
1388 conf.CHECK_LIB('sendfile')
1389 if not Options.options.with_sendfile_support == False:
1390 if (host_os.rfind('linux') > -1) or (host_os.rfind('gnu') > -1) or (host_os.rfind('k*bsd*-gnu') > -1) or (host_os.rfind('kopensolaris*-gnu') > -1):
1391 conf.CHECK_CODE('''
1392 int tofd, fromfd;
1393 off_t offset;
1394 size_t total;
1395 ssize_t nwritten = sendfile(tofd, fromfd, &offset, total);
1396 ''',
1397 '_HAVE_SENDFILE',
1398 headers='sys/sendfile.h',
1399 msg='Checking for linux sendfile support')
1401 if conf.CONFIG_SET('_HAVE_SENDFILE'):
1402 conf.DEFINE('HAVE_SENDFILE', '1')
1403 conf.DEFINE('LINUX_SENDFILE_API', '1')
1404 elif (host_os.rfind('freebsd') > -1) or (host_os.rfind('dragonfly') > -1):
1405 conf.CHECK_CODE('''
1406 #include <sys/types.h>
1407 #include <unistd.h>
1408 #include <sys/socket.h>
1409 #include <sys/uio.h>
1410 int fromfd, tofd, ret, total=0;
1411 off_t offset, nwritten;
1412 struct sf_hdtr hdr;
1413 struct iovec hdtrl;
1414 hdr.headers = &hdtrl;
1415 hdr.hdr_cnt = 1;
1416 hdr.trailers = NULL;
1417 hdr.trl_cnt = 0;
1418 hdtrl.iov_base = NULL;
1419 hdtrl.iov_len = 0;
1420 ret = sendfile(fromfd, tofd, offset, total, &hdr, &nwritten, 0)
1421 ''',
1422 '_HAVE_SENDFILE',
1423 msg='Checking for freebsd sendfile support')
1424 if conf.CONFIG_SET('_HAVE_SENDFILE'):
1425 conf.DEFINE('HAVE_SENDFILE', '1')
1426 conf.DEFINE('FREEBSD_SENDFILE_API', '1')
1427 elif (host_os.rfind('darwin') > -1):
1428 conf.CHECK_CODE('''
1429 #include <sys/types.h>
1430 #include <sys/socket.h>
1431 #include <sys/uio.h>
1432 int fromfd, tofd, ret;
1433 off_t offset, nwritten;
1434 struct sf_hdtr hdr;
1435 struct iovec hdtrl;
1436 hdr.headers = &hdtrl;
1437 hdr.hdr_cnt = 1;
1438 hdr.trailers = (void *)0;
1439 hdr.trl_cnt = 0;
1440 hdtrl.iov_base = (void *)0;
1441 hdtrl.iov_len = 0;
1442 ret = sendfile(fromfd, tofd, offset, &nwritten, &hdr, 0);
1443 ''',
1444 '_HAVE_SENDFILE',
1445 msg='Checking for darwin sendfile support')
1446 if conf.CONFIG_SET('_HAVE_SENDFILE'):
1447 conf.DEFINE('HAVE_SENDFILE', '1')
1448 conf.DEFINE('DARWIN_SENDFILE_API', '1')
1449 elif (host_os.rfind('hpux') > -1) or (host_os.rfind('osf') > -1):
1450 conf.CHECK_CODE('''
1451 #include <sys/socket.h>
1452 #include <sys/uio.h>
1453 int fromfd, tofd;
1454 size_t total=0;
1455 struct iovec hdtrl[2];
1456 ssize_t nwritten;
1457 off_t offset;
1458 hdtrl[0].iov_base = 0;
1459 hdtrl[0].iov_len = 0;
1460 nwritten = sendfile(tofd, fromfd, offset, total, &hdtrl[0], 0);
1461 ''',
1462 '_HAVE_SENDFILE',
1463 msg='Checking for osf/hpux sendfile support')
1464 if conf.CONFIG_SET('_HAVE_SENDFILE'):
1465 conf.DEFINE('HAVE_SENDFILE', '1')
1466 conf.DEFINE('HPUX_SENDFILE_API', '1')
1467 elif (host_os.rfind('sunos') > -1):
1468 conf.CHECK_FUNCS_IN('sendfilev', 'sendfile')
1469 conf.CHECK_CODE('''
1470 #include <sys/sendfile.h>,
1471 int sfvcnt;
1472 size_t xferred;
1473 struct sendfilevec vec[2];
1474 ssize_t nwritten;
1475 int tofd;
1476 sfvcnt = 2;
1477 vec[0].sfv_fd = SFV_FD_SELF;
1478 vec[0].sfv_flag = 0;
1479 vec[0].sfv_off = 0;
1480 vec[0].sfv_len = 0;
1481 vec[1].sfv_fd = 0;
1482 vec[1].sfv_flag = 0;
1483 vec[1].sfv_off = 0;
1484 vec[1].sfv_len = 0;
1485 nwritten = sendfilev(tofd, vec, sfvcnt, &xferred);
1486 ''',
1487 '_HAVE_SENDFILEV',
1488 msg='Checking for solaris sendfilev support',
1489 lib='sendfile')
1490 if conf.CONFIG_SET('_HAVE_SENDFILEV'):
1491 conf.DEFINE('HAVE_SENDFILEV', '1')
1492 conf.DEFINE('SOLARIS_SENDFILE_API', '1')
1493 elif (host_os.rfind('aix') > -1):
1494 conf.CHECK_CODE('''
1495 #include <sys/socket.h>
1496 int fromfd, tofd;
1497 size_t total=0;
1498 struct sf_parms hdtrl;
1499 ssize_t nwritten;
1500 hdtrl.header_data = 0;
1501 hdtrl.header_length = 0;
1502 hdtrl.file_descriptor = fromfd;
1503 hdtrl.file_offset = 0;
1504 hdtrl.file_bytes = 0;
1505 hdtrl.trailer_data = 0;
1506 hdtrl.trailer_length = 0;
1507 nwritten = send_file(&tofd, &hdtrl, 0);
1508 ''',
1509 '_HAVE_SENDFILE',
1510 msg='Checking for AIX send_file support')
1511 if conf.CONFIG_SET('_HAVE_SENDFILE'):
1512 conf.DEFINE('HAVE_SENDFILE', '1')
1513 conf.DEFINE('AIX_SENDFILE_API', '1')
1515 if Options.options.with_sendfile_support == True and not conf.CONFIG_SET('HAVE_SENDFILE'):
1516 conf.fatal('sendfile support not found but it was requested !')
1517 # Check for getcwd allowing a NULL arg.
1518 conf.CHECK_CODE('''
1519 #include <unistd.h>
1520 main() {
1521 char *s = getcwd(NULL,0);
1522 exit(s != NULL ? 0 : 1);
1523 }''', 'GETCWD_TAKES_NULL', addmain=False, execute=True,
1524 msg="getcwd takes a NULL argument")
1527 # UnixWare 7.x has its getspnam in -lgen
1528 conf.CHECK_FUNCS_IN('getspnam', 'gen')
1529 conf.CHECK_FUNCS_IN('getspnam', 'security')
1530 conf.CHECK_FUNCS_IN('getspnam', 'sec')
1532 legacy_quota_libs = ''
1533 if not Options.options.with_quotas == False:
1534 # For quotas on Veritas VxFS filesystems
1535 conf.CHECK_HEADERS('sys/fs/vx_quota.h')
1536 # For sys/quota.h and linux/quota.h
1537 conf.CHECK_HEADERS('sys/quota.h')
1538 # For quotas on BSD systems
1539 conf.CHECK_HEADERS('ufs/ufs/quota.h')
1540 # For quotas on AIX systems
1541 conf.CHECK_HEADERS('jfs/quota.h')
1542 # For quotas on Linux XFS filesystems
1543 if conf.CHECK_HEADERS('xfs/xqm.h'):
1544 conf.DEFINE('HAVE_XFS_QUOTAS', '1')
1545 else:
1546 # For Irix XFS
1547 conf.CHECK_CODE('''
1548 #include "confdefs.h"
1549 #ifdef HAVE_SYS_TYPES_H
1550 #include <sys/types.h>
1551 #endif
1552 #ifdef HAVE_ASM_TYPES_H
1553 #include <asm/types.h>
1554 #endif
1555 #include <sys/quota.h>
1556 int i = Q_XGETQUOTA;''',
1557 define='HAVE_XFS_QUOTAS',
1558 msg='for XFS QUOTA in <sys/quota.h>',
1559 execute=False,
1560 local_include=False)
1562 # For IRIX like dqb_isoftlimit instead of dqb_fsoftlimit in struc dqblk
1563 conf.CHECK_STRUCTURE_MEMBER('struct dqblk', 'dqb_fsoftlimit', define='HAVE_DQB_FSOFTLIMIT',
1564 headers='sys/quota.h')
1565 #darwin style quota bytecount
1566 conf.CHECK_STRUCTURE_MEMBER('struct dqblk', 'dqb_curbytes', define='HAVE_STRUCT_DQBLK_DQB_CURBYTES',
1567 headers='sys/quota.h')
1568 conf.CHECK_HEADERS('rpc/types.h rpc/xdr.h', together=True)
1569 if conf.CHECK_HEADERS('rpcsvc/rquota.h', lib='tirpc'):
1570 # Optional structure member
1571 conf.CHECK_STRUCTURE_MEMBER('struct getquota_rslt', 'getquota_rslt_u',
1572 define='HAVE_GETQUOTA_RSLT_GETQUOTA_RSLT_U',
1573 headers='rpcsvc/rquota.h',
1574 lib='tirpc')
1576 # Required function for NFS quota support
1577 conf.CHECK_CODE('''
1578 clnt_create("", RQUOTAPROG, RQUOTAVERS, "udp");
1579 ''',
1580 headers="rpc/rpc.h rpc/types.h rpcsvc/rquota.h rpc/nettype.h rpc/xdr.h",
1581 define='HAVE_NFS_QUOTAS',
1582 msg='checking for clnt_create()',
1583 execute=True,
1584 local_include=False,
1585 lib='tirpc')
1587 if (host_os.rfind('linux') > -1):
1588 conf.DEFINE('HAVE_QUOTACTL_LINUX', '1')
1589 elif not conf.CONFIG_SET("HAVE_XFS_QUOTAS"):
1590 if not conf.CHECK_CODE('''
1591 #define HAVE_QUOTACTL_4A 1
1592 #define AUTOCONF_TEST 1
1593 #include "../tests/sysquotas.c"
1594 ''',
1595 cflags=conf.env['WERROR_CFLAGS'],
1596 define='HAVE_QUOTACTL_4A',
1597 msg='for QUOTACTL_4A: long quotactl(int cmd, char *special, qid_t id, caddr_t addr)',
1598 execute=True,
1599 addmain=False):
1601 conf.CHECK_CODE('''
1602 #define HAVE_QUOTACTL_4B 1
1603 #define AUTOCONF_TEST 1
1604 #include "../tests/sysquotas.c"
1605 ''',
1606 cflags=conf.env['WERROR_CFLAGS'],
1607 define='HAVE_QUOTACTL_4B',
1608 msg='for QUOTACTL_4B: int quotactl(const char *path, int cmd, int id, char *addr)',
1609 execute=True,
1610 addmain=False)
1612 if conf.CONFIG_SET('HAVE_QUOTACTL_LINUX') or \
1613 conf.CONFIG_SET('HAVE_QUOTACTL_4A') or \
1614 conf.CONFIG_SET('HAVE_QUOTACTL_4B') or \
1615 conf.CONFIG_SET('HAVE_XFS_QUOTAS'):
1616 conf.DEFINE('HAVE_SYS_QUOTAS', '1')
1617 conf.DEFINE('WITH_QUOTAS', '1')
1620 # check if Legacy quota code can be brought in
1621 # if standard interfaces are not supported
1623 if not conf.CONFIG_SET('WITH_QUOTAS'):
1624 if host_os.rfind('sunos5') > -1:
1625 conf.DEFINE('SUNOS5', '1')
1626 legacy_quota_libs = 'nsl'
1627 conf.CHECK_CODE('''
1628 #define WITH_QUOTAS 1
1629 #define AUTOCONF_TEST 1
1630 #include "../tests/oldquotas.c"
1631 ''',
1632 cflags=conf.env['WERROR_CFLAGS'],
1633 define='WITH_QUOTAS',
1634 lib=legacy_quota_libs,
1635 msg='Checking whether legacy quota code can be used',
1636 execute=False,
1637 addmain=False)
1638 if not conf.CONFIG_SET('WITH_QUOTAS'):
1639 legacy_quota_libs = ''
1640 conf.env['legacy_quota_libs'] = legacy_quota_libs
1642 if Options.options.with_quotas == True and not conf.CONFIG_SET('WITH_QUOTAS'):
1643 conf.fatal('quota support not found but it was requested !')
1645 conf.CHECK_CODE('(void)unshare(CLONE_FS);',
1646 headers='sched.h',
1647 define='HAVE_UNSHARE_CLONE_FS',
1648 msg='for Linux unshare(CLONE_FS)')
1650 # Check for mallinfo
1651 conf.CHECK_CODE('''
1652 struct mallinfo mi;
1653 int tmp;
1655 mi = mallinfo();
1656 tmp = mi.arena + mi.ordblks + mi.smblks + mi.hblks +
1657 mi.hblkhd + mi.usmblks + mi.fsmblks + mi.uordblks +
1658 mi.fordblks + mi.keepcost;
1659 return tmp;
1660 ''', 'HAVE_MALLINFO', msg="Checking for mallinfo()", headers='malloc.h')
1663 # cluster support (CTDB)
1665 if not Options.options.with_cluster_support:
1666 Logs.info("building without cluster support (--without-cluster-support)")
1667 conf.env.with_ctdb = False
1668 else:
1669 Logs.info("building with cluster support")
1670 conf.env.with_ctdb = True
1671 conf.DEFINE('CLUSTER_SUPPORT', 1)
1673 conf.CHECK_CODE('void seekdir(DIR *d, long loc) { return; }',
1674 'SEEKDIR_RETURNS_VOID',
1675 headers='sys/types.h dirent.h',
1676 msg='Checking whether seekdir returns void')
1678 if Options.options.with_profiling_data:
1679 conf.DEFINE('WITH_PROFILE', 1);
1680 conf.CHECK_FUNCS('getrusage', headers="sys/time.h sys/resource.h")
1682 if (conf.CHECK_HEADERS('linux/ioctl.h sys/ioctl.h linux/fs.h') and
1683 conf.CHECK_DECLS('FS_IOC_GETFLAGS FS_COMPR_FL', headers='linux/fs.h')):
1684 conf.DEFINE('HAVE_LINUX_IOCTL', '1')
1686 conf.env['CFLAGS_CEPHFS'] = "-D_FILE_OFFSET_BITS=64"
1687 if Options.options.libcephfs_dir:
1688 Logs.error('''--with-libcephfs no longer supported, please use compiler
1689 flags instead, e.g. GCC LIBRARY_PATH and C_INCLUDE_PATH''')
1690 sys.exit(1)
1692 if (Options.options.with_cephfs and
1693 conf.CHECK_HEADERS('cephfs/libcephfs.h', False, False, 'cephfs') and
1694 conf.CHECK_LIB('cephfs', shlib=True)):
1695 if (Options.options.with_acl_support and
1696 conf.CHECK_FUNCS_IN('ceph_statx', 'cephfs',
1697 headers='cephfs/libcephfs.h')):
1698 conf.DEFINE('HAVE_CEPH', '1')
1699 else:
1700 Logs.warn('''Ceph support disabled due to --without-acl-support
1701 or lack of ceph_statx support''')
1702 conf.undefine('HAVE_CEPH')
1704 if Options.options.with_glusterfs:
1705 conf.CHECK_CFG(package='glusterfs-api', args='"glusterfs-api >= 4" --cflags --libs',
1706 msg='Checking for glusterfs-api >= 4', uselib_store="GFAPI")
1707 conf.CHECK_HEADERS('glusterfs/api/glfs.h', lib='gfapi')
1708 conf.CHECK_LIB('gfapi', shlib=True)
1710 if conf.CONFIG_SET('HAVE_GLUSTERFS_API_GLFS_H'):
1711 if Options.options.with_acl_support:
1712 conf.DEFINE('HAVE_GLUSTERFS', '1')
1713 else:
1714 Logs.warn("GlusterFS support disabled due to --without-acl-support")
1715 conf.undefine('HAVE_GLUSTERFS')
1716 else:
1717 conf.undefine('HAVE_GLUSTERFS')
1719 conf.CHECK_CFG(package='glusterfs-api', args='"glusterfs-api >= 6" --cflags --libs',
1720 msg='Checking for glusterfs-api >= 6',
1721 uselib_store="GFAPI_VER_6")
1722 conf.CHECK_CFG(package='glusterfs-api', args='"glusterfs-api >= 7.6" --cflags --libs',
1723 msg='Checking for glusterfs-api >= 7.6',
1724 uselib_store="GFAPI_VER_7_6")
1725 conf.CHECK_CFG(package='glusterfs-api', args='"glusterfs-api >= 7.9" --cflags --libs',
1726 msg='Checking for glusterfs-api >= 7.9',
1727 uselib_store="GFAPI_VER_7_9")
1728 else:
1729 conf.SET_TARGET_TYPE('gfapi', 'EMPTY')
1730 conf.undefine('HAVE_GLUSTERFS')
1732 if Options.options.enable_vxfs:
1733 conf.DEFINE('HAVE_VXFS', '1')
1735 if conf.CHECK_CFG(package='liburing', args='--cflags --libs',
1736 msg='Checking for liburing package', uselib_store="URING"):
1737 if (conf.CHECK_HEADERS('liburing.h', lib='uring')
1738 and conf.CHECK_LIB('uring', shlib=True)):
1739 conf.CHECK_FUNCS_IN('io_uring_ring_dontfork', 'uring',
1740 headers='liburing.h')
1741 conf.DEFINE('HAVE_LIBURING', '1')
1743 conf.env.build_regedit = False
1744 if not Options.options.with_regedit == False:
1745 conf.PROCESS_SEPARATE_RULE('system_ncurses')
1746 if conf.CONFIG_SET('HAVE_NCURSES'):
1747 conf.env.build_regedit = True
1749 if conf.env.build_regedit:
1750 Logs.info("building regedit")
1751 else:
1752 if Options.options.with_regedit == False:
1753 Logs.info("not building regedit (--without-regedit)")
1754 elif Options.options.with_regedit == True:
1755 Logs.error("ncurses not available, cannot build regedit")
1756 conf.fatal("ncurses not available, but --with-regedit was specified")
1757 else:
1758 Logs.info("ncurses not available, not building regedit")
1760 if conf.CHECK_HEADERS('ftw.h') and conf.CHECK_FUNCS('nftw'):
1761 conf.env.build_mvxattr = True
1763 conf.env.build_winexe = False
1764 if not Options.options.with_winexe == False:
1765 if conf.CONFIG_SET('HAVE_WINEXE_CC_WIN32') or conf.CONFIG_SET('HAVE_WINEXE_CC_WIN64'):
1766 conf.env.build_winexe = True
1768 if conf.env.build_winexe:
1769 Logs.info("building winexe")
1770 else:
1771 if Options.options.with_winexe == False:
1772 Logs.info("not building winexe (--without-winexe)")
1773 elif Options.options.with_winexe == True:
1774 Logs.error("mingw not available, cannot build winexe")
1775 conf.fatal("mingw not available, but --with-winexe was specified")
1776 else:
1777 Logs.info("mingw not available, not building winexe")
1779 conf.CHECK_FUNCS_IN('DES_pcbc_encrypt', 'crypto')
1780 if Options.options.with_fake_kaserver == True:
1781 conf.CHECK_HEADERS('afs/param.h afs/stds.h', together=True)
1782 conf.CHECK_HEADERS('afs/param.h afs/stds.h', together=True)
1783 if (conf.CONFIG_SET('HAVE_AFS_PARAM_H') and conf.CONFIG_SET('HAVE_AFS_STDS_H') and conf.CONFIG_SET('HAVE_DES_PCBC_ENCRYPT')):
1784 conf.DEFINE('WITH_FAKE_KASERVER', '1')
1785 else:
1786 conf.fatal('AFS headers not available, but --with-fake-kaserver was specified')
1788 if conf.CHECK_CFG(package='glib-2.0',
1789 args='--cflags --libs',
1790 msg='Checking for glib-2.0',
1791 uselib_store="GLIB-2.0"):
1792 if (conf.CHECK_HEADERS('glib.h', lib='glib-2.0') and conf.CHECK_LIB('glib-2.0', shlib=True)):
1793 conf.DEFINE('HAVE_GLIB', 1)
1795 if conf.CONFIG_SET('HAVE_GLIB'):
1796 conf.DEFINE('WITH_TEVENT_GLIB_GLUE', '1')
1798 conf.env['libtracker']=''
1799 tracker_versions = ['2.0', '1.0', '0.16', '0.14']
1801 for version in tracker_versions:
1802 testlib = 'tracker-sparql-' + version
1803 if conf.CHECK_CFG(package=testlib,
1804 args='--cflags --libs',
1805 mandatory=False):
1806 conf.SET_TARGET_TYPE(testlib, 'SYSLIB')
1807 conf.env['libtracker'] = testlib
1808 conf.DEFINE('HAVE_TRACKER', '1')
1809 break
1811 with_spotlight_tracker_backend = (
1812 conf.CONFIG_SET('HAVE_TRACKER')
1813 and conf.CONFIG_SET('HAVE_GLIB')
1814 and conf.env['BISON']
1815 and conf.env['FLEX']
1816 and conf.CONFIG_GET('HAVE_UTF8_NORMALISATION')
1819 with_spotlight_es_backend = (
1820 conf.CONFIG_SET('HAVE_JSON_OBJECT')
1821 and conf.env['BISON']
1822 and conf.env['FLEX']
1823 and conf.CONFIG_GET('HAVE_UTF8_NORMALISATION')
1826 conf.env.with_spotlight = False
1827 if Options.options.with_spotlight is not False:
1828 backends = ['noindex']
1830 if not conf.env['BISON']:
1831 Logs.warn("Spotlight support requested but bison missing")
1832 if not conf.env['FLEX']:
1833 Logs.warn("Spotlight support requested but flex missing")
1834 if not conf.CONFIG_GET('HAVE_UTF8_NORMALISATION'):
1835 Logs.warn("Missing support for Unicode normalisation. "
1836 "Try installing icu-dev or libicu-devel.")
1837 if not conf.CONFIG_SET('HAVE_TRACKER'):
1838 Logs.warn('Missing libtracker-sparql development files for Spotlight backend "tracker"')
1839 if not conf.CONFIG_SET('HAVE_GLIB'):
1840 Logs.warn('Missing glib-2.0 development files for Spotlight backend "tracker"')
1841 if not conf.CONFIG_GET('HAVE_JSON_OBJECT'):
1842 Logs.warn('Missing libjansson development files for Spotlight backend "elasticsearch"')
1844 if with_spotlight_tracker_backend:
1845 conf.env.spotlight_backend_tracker = True
1846 backends.append('tracker')
1847 conf.DEFINE('HAVE_SPOTLIGHT_BACKEND_TRACKER', '1')
1849 if with_spotlight_es_backend:
1850 conf.env.spotlight_backend_es = True
1851 backends.append('elasticsearch')
1852 conf.DEFINE('HAVE_SPOTLIGHT_BACKEND_ES', '1')
1854 if (Options.options.with_spotlight is True
1855 and not conf.env.spotlight_backend_tracker
1856 and not conf.env.spotlight_backend_es):
1857 conf.fatal("Unmet dependencies for Spotlight backends")
1859 Logs.info("Building with Spotlight support, available backends: %s" % ', '.join(backends))
1860 conf.DEFINE('WITH_SPOTLIGHT', '1')
1861 conf.env.with_spotlight = True
1863 if not conf.CONFIG_SET('HAVE_RPC_XDR_H'):
1864 conf.CHECK_HEADERS('rpc/types.h rpc/xdr.h', together=True, lib='tirpc')
1866 if conf.CHECK_FUNCS_IN('nscd_flush_cache', 'nscd', headers='libnscd.h'):
1867 conf.DEFINE('HAVE_NSCD_FLUSH_CACHE', '1')
1869 forced_static_modules.extend(['auth_builtin', 'auth_sam', 'auth_winbind'])
1870 default_static_modules.extend(['pdb_smbpasswd', 'pdb_tdbsam',
1871 'auth_unix',
1872 'nss_info_template', 'idmap_tdb', 'idmap_passdb',
1873 'idmap_nss'])
1875 default_shared_modules.extend(['vfs_recycle', 'vfs_audit', 'vfs_extd_audit', 'vfs_full_audit',
1876 'vfs_fake_perms', 'vfs_default_quota', 'vfs_readonly', 'vfs_cap',
1877 'vfs_expand_msdfs', 'vfs_shadow_copy', 'vfs_shadow_copy2',
1878 'vfs_readahead', 'vfs_xattr_tdb',
1879 'vfs_streams_xattr', 'vfs_streams_depot', 'vfs_acl_xattr', 'vfs_acl_tdb',
1880 'vfs_preopen', 'vfs_catia',
1881 'vfs_media_harmony', 'vfs_unityed_media', 'vfs_fruit', 'vfs_shell_snap',
1882 'vfs_commit', 'vfs_worm', 'vfs_crossrename', 'vfs_linux_xfs_sgid',
1883 'vfs_time_audit', 'vfs_offline', 'vfs_virusfilter', 'vfs_widelinks'])
1884 if host_os.rfind('linux') > -1:
1885 default_shared_modules.extend(['vfs_snapper'])
1887 default_shared_modules.extend(['idmap_tdb2', 'idmap_script'])
1888 # these have broken dependencies
1889 forced_shared_modules.extend(['idmap_autorid', 'idmap_rid', 'idmap_hash'])
1891 if Options.options.developer:
1892 default_static_modules.extend(['charset_weird'])
1893 default_shared_modules.extend(['perfcount_test',
1894 'vfs_skel_opaque', 'vfs_skel_transparent', 'vfs_shadow_copy_test',
1895 'pdb_test',
1896 'vfs_fake_dfq',
1897 'gpext_security', 'gpext_registry', 'gpext_scripts'])
1899 if Options.options.enable_selftest or Options.options.developer:
1900 default_shared_modules.extend(['vfs_fake_acls', 'vfs_nfs4acl_xattr',
1901 'vfs_error_inject',
1902 'vfs_delay_inject'])
1904 if conf.CONFIG_SET('AD_DC_BUILD_IS_ENABLED'):
1905 default_static_modules.extend(['pdb_samba_dsdb', 'auth_samba4', 'vfs_dfs_samba4'])
1906 default_shared_modules.extend(['vfs_posix_eadb'])
1908 if conf.CONFIG_SET('HAVE_FREEBSD_SUNACL_H'):
1909 default_shared_modules.extend(['vfs_zfsacl'])
1911 if conf.CONFIG_SET('HAVE_DIRFD_DECL'):
1912 default_shared_modules.extend(['vfs_syncops', 'vfs_dirsort'])
1914 if conf.CONFIG_SET('HAVE_STATFS_F_FSID'):
1915 default_shared_modules.extend(['vfs_fileid'])
1917 if (conf.CONFIG_SET('HAVE_STRUCT_MSGHDR_MSG_CONTROL') or conf.CONFIG_SET('HAVE_STRUCT_MSGHDR_MSG_ACCRIGHTS')):
1918 default_shared_modules.extend(['vfs_aio_fork'])
1920 if conf.CONFIG_SET('HAVE_LIBURING'):
1921 default_shared_modules.extend(['vfs_io_uring'])
1923 if Options.options.with_pthreadpool:
1924 default_shared_modules.extend(['vfs_aio_pthread'])
1926 if conf.CONFIG_SET('HAVE_LDAP'):
1927 default_static_modules.extend(['pdb_ldapsam', 'idmap_ldap'])
1929 if conf.CONFIG_SET('DARWINOS'):
1930 default_static_modules.extend(['charset_macosxfs'])
1932 if conf.CONFIG_SET('HAVE_GPFS') and conf.CONFIG_SET('HAVE_KERNEL_OPLOCKS_LINUX'):
1933 default_shared_modules.extend(['vfs_gpfs'])
1935 if (conf.CONFIG_SET('HAVE_LINUX_IOCTL')
1936 and conf.CONFIG_SET('HAVE_BASENAME') and conf.CONFIG_SET('HAVE_DIRNAME')):
1937 default_shared_modules.extend(['vfs_btrfs'])
1939 if conf.CONFIG_SET("HAVE_CEPH"):
1940 default_shared_modules.extend(['vfs_ceph'])
1941 # Unlike vfs_ceph, vfs_ceph_snapshots doesn't depend on libcephfs, so
1942 # can be enabled atop a kernel CephFS share (with vfs_default) in
1943 # addition to vfs_ceph. Still, only enable vfs_ceph_snapshots builds
1944 # if we're building with libcephfs for now.
1945 default_shared_modules.extend(['vfs_ceph_snapshots'])
1947 if conf.CONFIG_SET('HAVE_GLUSTERFS'):
1948 default_shared_modules.extend(['vfs_glusterfs'])
1950 if conf.CONFIG_SET('HAVE_SETMNTENT'):
1951 default_shared_modules.extend(['vfs_glusterfs_fuse'])
1953 if conf.CONFIG_SET('HAVE_VXFS'):
1954 default_shared_modules.extend(['vfs_vxfs'])
1956 explicit_shared_modules = TO_LIST(Options.options.shared_modules, delimiter=',')
1957 explicit_static_modules = TO_LIST(Options.options.static_modules, delimiter=',')
1959 def replace_list_item(lst, item, value):
1960 try:
1961 idx = lst.index(item)
1962 lst[idx] = value
1963 except:
1964 pass
1965 # PDB module file name should have the same name as module registers itself
1966 # In Autoconf build we export LDAP passdb module as ldapsam but WAF build
1967 # was always exporting pdb_ldap. In order to support existing packages
1968 # allow referring to pdb_ldapsam as pdb_ldap but use proper name internally.
1969 replace_list_item(explicit_shared_modules, 'pdb_ldap', 'pdb_ldapsam')
1970 replace_list_item(explicit_static_modules, 'pdb_ldap', 'pdb_ldapsam')
1972 final_static_modules = []
1973 final_static_modules.extend(TO_LIST(required_static_modules))
1974 final_shared_modules = []
1976 if '!FORCED' not in explicit_static_modules:
1977 final_static_modules.extend(TO_LIST(forced_static_modules))
1978 if '!FORCED' not in explicit_shared_modules:
1979 final_shared_modules.extend(TO_LIST(forced_shared_modules))
1980 if '!DEFAULT' not in explicit_static_modules:
1981 final_static_modules.extend(TO_LIST(default_static_modules))
1982 if '!DEFAULT' not in explicit_shared_modules:
1983 final_shared_modules.extend(TO_LIST(default_shared_modules))
1985 if 'ALL' in explicit_static_modules:
1986 for m in default_shared_modules:
1987 if m in final_shared_modules:
1988 final_shared_modules.remove(m)
1989 final_static_modules.append(m)
1990 if 'ALL' in explicit_shared_modules:
1991 for m in default_static_modules:
1992 if m in final_static_modules:
1993 final_static_modules.remove(m)
1994 final_shared_modules.append(m)
1996 for m in explicit_static_modules:
1997 if m in ['ALL','!DEFAULT','!FORCED']:
1998 continue
1999 if m.startswith('!'):
2000 m = m[1:]
2001 if m in required_static_modules:
2002 raise Errors.WafError('These modules are REQUIRED as static modules: %s' %
2003 ' '.join(required_static_modules))
2004 if m in final_static_modules:
2005 final_static_modules.remove(m)
2006 continue
2007 if m in forced_shared_modules:
2008 raise Errors.WafError('These modules MUST be configured as shared modules: %s' %
2009 ' '.join(forced_shared_modules))
2010 if m in final_shared_modules:
2011 final_shared_modules.remove(m)
2012 if m not in final_static_modules:
2013 final_static_modules.append(m)
2014 for m in explicit_shared_modules:
2015 if m in ['ALL','!DEFAULT','!FORCED']:
2016 continue
2017 if m.startswith('!'):
2018 m = m[1:]
2019 if m in final_shared_modules:
2020 final_shared_modules.remove(m)
2021 continue
2022 if m in required_static_modules:
2023 raise Errors.WafError('These modules are REQUIRED as static modules: %s' %
2024 ' '.join(required_static_modules))
2025 if m in forced_static_modules:
2026 raise Errors.WafError('These module MUST be configured as static modules: %s' %
2027 ' '.join(forced_static_modules))
2028 if m in final_static_modules:
2029 final_static_modules.remove(m)
2030 if m not in final_shared_modules:
2031 final_shared_modules.append(m)
2033 conf.env['static_modules'] = final_static_modules
2034 conf.env['shared_modules'] = final_shared_modules
2036 conf.DEFINE('STRING_STATIC_MODULES', ' '.join(final_static_modules), quote=True)
2037 conf.DEFINE('STRING_SHARED_MODULES', ' '.join(final_shared_modules), quote=True)
2039 static_list = {}
2040 shared_list = {}
2042 prefixes = ['vfs', 'pdb', 'auth', 'nss_info', 'charset', 'idmap', 'gpext', 'perfcount']
2043 conf.env['MODULE_PREFIXES'] = prefixes
2044 for p in prefixes:
2045 for m in final_static_modules:
2046 if m.find(p) == 0:
2047 if not p in static_list:
2048 static_list[p] = []
2049 static_list[p].append(m)
2050 for m in final_shared_modules:
2051 if m.find(p) == 0:
2052 if not p in shared_list:
2053 shared_list[p] = []
2054 shared_list[p].append(m)
2056 for p in prefixes:
2057 static_env = "%s_STATIC" % p.upper()
2058 shared_env = "%s_SHARED" % p.upper()
2059 conf.env[static_env] = []
2060 conf.env[shared_env] = []
2061 if p in static_list:
2062 decl_list = " ".join("extern NTSTATUS %s_init(TALLOC_CTX *mem_ctx); " % entry for entry in static_list[p])
2063 for entry in static_list[p]:
2064 conf.env[static_env].append('%s' % entry)
2065 conf.DEFINE('static_decl_%s' % p, decl_list)
2066 conf.DEFINE('static_init_%s(mem_ctx)' % p, '{ %s_init((mem_ctx)); }' % '_init((mem_ctx)); '.join(static_list[p]))
2067 else:
2068 conf.DEFINE('static_decl_%s' % p, '')
2069 conf.DEFINE('static_init_%s(mem_ctx)' % p, '{}')
2070 if p in shared_list:
2071 for entry in shared_list[p]:
2072 conf.DEFINE('%s_init' % entry, 'samba_init_module')
2073 conf.env[shared_env].append('%s' % entry)
2074 Logs.info("%s: %s" % (static_env, ','.join(conf.env[static_env])))
2075 Logs.info("%s: %s" % (shared_env, ','.join(conf.env[shared_env])))
2077 if (('vfs_snapper' in shared_list.get('vfs', []) or 'vfs_snapper' in static_list.get('vfs', []))
2078 and not (conf.CHECK_CFG(package='dbus-1', args='--cflags --libs',
2079 msg='Checking for dbus', uselib_store="DBUS-1")
2080 and conf.CHECK_HEADERS('dbus/dbus.h', lib='dbus-1')
2081 and conf.CHECK_LIB('dbus-1', shlib=True))):
2082 conf.fatal("vfs_snapper is enabled but prerequisite dbus-1 package not "
2083 "found. Use --with-shared-modules='!vfs_snapper' to disable "
2084 "vfs_snapper support.")
2086 conf.SAMBA_CONFIG_H('include/config.h')