/*
    clsync - file tree sync utility based on inotify/kqueue

    Copyright (C) 2013-2014 Dmitry Yu Okunev <dyokunev@ut.mephi.ru> 0x8E30679C

    This program is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

#ifdef HL_LOCK_TRIES_AUTO
# define IF_HL_LOCK_TRIES_AUTO(a) a
#else
# define IF_HL_LOCK_TRIES_AUTO(a) {}
#endif

#ifdef CAPABILITIES_SUPPORT

enum priv_callid {
	PC_DEFAULT = 0,
	PC_SYNC_INIIALSYNC_WALK_FTS_OPEN,
	PC_SYNC_INIIALSYNC_WALK_FTS_READ,
	PC_SYNC_INIIALSYNC_WALK_FTS_CLOSE,
	PC_SYNC_MARK_WALK_FTS_OPEN,
	PC_SYNC_MARK_WALK_FTS_READ,
	PC_SYNC_MARK_WALK_FTS_CLOSE,
	PC_INOTIFY_ADD_WATCH_DIR,

	PC_MON_HANDLE_LSTAT64,

	PC_MAX
};

extern int ( *_privileged_lstat64 )		(
    const char *path, stat64_t *buf
# ifdef HL_LOCK_TRIES_AUTO
    , int callid
# endif
);

extern FTS * ( *_privileged_fts_open )		(
    char * const *path_argv,
    int options,
    int ( *compar ) ( const FTSENT **, const FTSENT ** )
# ifdef HL_LOCK_TRIES_AUTO
    , int callid
# endif
);

extern FTSENT * ( *_privileged_fts_read )		(
    FTS *ftsp
# ifdef HL_LOCK_TRIES_AUTO
    , int callid
# endif
);

extern int ( *_privileged_fts_close )		(
    FTS *ftsp
# ifdef HL_LOCK_TRIES_AUTO
    , int callid
# endif
);

extern int ( *_privileged_inotify_init )		();
extern int ( *_privileged_inotify_init1 )		( int flags );

extern int ( *_privileged_inotify_add_watch )	(
    int fd,
    const char *pathname,
    uint32_t mask
# ifdef HL_LOCK_TRIES_AUTO
    , int callid
# endif
);

extern int ( *_privileged_inotify_rm_watch )	(
    int fd,
    int wd
);

#ifdef CGROUP_SUPPORT
extern int ( *_privileged_clsync_cgroup_deinit )	( ctx_t *ctx_p );
#endif

extern pid_t ( *_privileged_waitpid )		( pid_t pid, int *status, int options );

extern int privileged_check();

# ifdef HL_LOCK_TRIES_AUTO
#  define privileged_lstat64(a,b,c)		_privileged_lstat64(a,b,c)
#  define privileged_fts_open(a,b,c,d)		_privileged_fts_open(a,b,c,d)
#  define privileged_fts_read(a,b)		_privileged_fts_read(a,b)
#  define privileged_fts_close(a,b)		_privileged_fts_close(a,b)
#  define privileged_inotify_add_watch(a,b,c,d)	_privileged_inotify_add_watch(a,b,c,d)
# else
#  define privileged_lstat64(a,b,c)		_privileged_lstat64(a,b)
#  define privileged_fts_open(a,b,c,d)		_privileged_fts_open(a,b,c)
#  define privileged_fts_read(a,b)		_privileged_fts_read(a)
#  define privileged_fts_close(a,b)		_privileged_fts_close(a)
#  define privileged_inotify_add_watch(a,b,c,d)	_privileged_inotify_add_watch(a,b,c)
# endif

# define privileged_inotify_init		_privileged_inotify_init
# define privileged_inotify_init1		_privileged_inotify_init1
# define privileged_inotify_rm_watch		_privileged_inotify_rm_watch
# define privileged_clsync_cgroup_deinit	_privileged_clsync_cgroup_deinit
# define privileged_waitpid			_privileged_waitpid

#else

# define privileged_check(...)			{}

# define privileged_lstat64(a,b,c)		lstat64(a,b)
# define privileged_fts_open(a,b,c,d)		fts_open(a,b,c)
# define privileged_fts_read(a,b)		fts_read(a)
# define privileged_fts_close(a,b)		fts_close(a)
# define privileged_inotify_init		inotify_init
# define privileged_inotify_init1		inotify_init1
# define privileged_inotify_add_watch(a,b,c,d)	inotify_add_watch(a,b,c)
# define privileged_inotify_rm_watch		inotify_rm_watch
# ifdef CGROUP_SUPPORT
#  define privileged_clsync_cgroup_deinit	clsync_cgroup_deinit
# endif
# define privileged_waitpid			waitpid
#endif

extern int ( *_privileged_kill_child ) (
    pid_t pid,
    int   sig,
    char  ignoreerrors
);

extern int ( *_privileged_fork_execvp ) (
    const char *file,
    char *const argv[]
);

#define privileged_kill_child			_privileged_kill_child
#define privileged_fork_execvp			_privileged_fork_execvp

extern int privileged_init ( struct ctx *ctx_p );
extern int privileged_deinit ( struct ctx *ctx_p );

