Skip to content
Snippets Groups Projects
utils.c 73.6 KiB
Newer Older
  • Learn to ignore specific revisions
  • int ast_file_is_readable(const char *filename)
    {
    #if defined(HAVE_EACCESS) || defined(HAVE_EUIDACCESS)
    #if defined(HAVE_EUIDACCESS) && !defined(HAVE_EACCESS)
    #define eaccess euidaccess
    #endif
    	return eaccess(filename, R_OK) == 0;
    #else
    	int fd = open(filename, O_RDONLY |  O_NONBLOCK);
    	if (fd < 0) {
    		return 0;
    	}
    	close(fd);
    	return 1;
    #endif
    }
    
    
    int ast_compare_versions(const char *version1, const char *version2)
    {
    
    	unsigned int major[2] = { 0 };
    	unsigned int minor[2] = { 0 };
    	unsigned int patch[2] = { 0 };
    	unsigned int extra[2] = { 0 };
    	int res;
    
    	sscanf(version1, "%u.%u.%u.%u", &major[0], &minor[0], &patch[0], &extra[0]);
    	sscanf(version2, "%u.%u.%u.%u", &major[1], &minor[1], &patch[1], &extra[1]);
    
    	res = major[0] - major[1];
    	if (res) {
    		return res;
    	}
    	res = minor[0] - minor[1];
    	if (res) {
    		return res;
    	}
    	res = patch[0] - patch[1];
    	if (res) {
    		return res;
    
    	return extra[0] - extra[1];
    
    
    int __ast_fd_set_flags(int fd, int flags, enum ast_fd_flag_operation op,
    	const char *file, int lineno, const char *function)
    {
    	int f;
    
    	f = fcntl(fd, F_GETFL);
    	if (f == -1) {
    		ast_log(__LOG_ERROR, file, lineno, function,
    			"Failed to get fcntl() flags for file descriptor: %s\n", strerror(errno));
    		return -1;
    	}
    
    	switch (op) {
    	case AST_FD_FLAG_SET:
    
    		if ((f & flags) == flags) {
    			/* There is nothing to set */
    			return 0;
    		}
    
    		f |= flags;
    		break;
    	case AST_FD_FLAG_CLEAR:
    
    		if (!(f & flags)) {
    			/* There is nothing to clear */
    			return 0;
    		}
    
    		f &= ~flags;
    		break;
    	default:
    		ast_assert(0);
    		break;
    	}
    
    	f = fcntl(fd, F_SETFL, f);
    	if (f == -1) {
    		ast_log(__LOG_ERROR, file, lineno, function,
    			"Failed to set fcntl() flags for file descriptor: %s\n", strerror(errno));
    		return -1;
    	}
    
    	return 0;
    }
    
    #ifndef HAVE_SOCK_NONBLOCK
    int ast_socket_nonblock(int domain, int type, int protocol)
    {
    	int s = socket(domain, type, protocol);
    	if (s < 0) {
    		return -1;
    	}
    
    	if (ast_fd_set_flags(s, O_NONBLOCK)) {
    		close(s);
    		return -1;
    	}
    
    	return s;
    }
    #endif
    
    #ifndef HAVE_PIPE2
    int ast_pipe_nonblock(int filedes[2])
    {
    	int p = pipe(filedes);
    	if (p < 0) {
    		return -1;
    	}
    
    	if (ast_fd_set_flags(filedes[0], O_NONBLOCK)
    	   || ast_fd_set_flags(filedes[1], O_NONBLOCK)) {
    		close(filedes[0]);
    		close(filedes[1]);
    		return -1;
    	}
    
    	return 0;
    }
    #endif
    
    
    /*!
     * \brief A thread local indicating whether the current thread is a user interface.
     */
    AST_THREADSTORAGE(thread_user_interface_tl);
    
    int ast_thread_user_interface_set(int is_user_interface)
    {
    	int *thread_user_interface;
    
    	thread_user_interface = ast_threadstorage_get(
    		&thread_user_interface_tl, sizeof(*thread_user_interface));
    	if (thread_user_interface == NULL) {
    		ast_log(LOG_ERROR, "Error setting user interface status for current thread\n");
    		return -1;
    	}
    
    	*thread_user_interface = !!is_user_interface;
    	return 0;
    }
    
    int ast_thread_is_user_interface(void)
    {
    	int *thread_user_interface;
    
    	thread_user_interface = ast_threadstorage_get(
    		&thread_user_interface_tl, sizeof(*thread_user_interface));
    	if (thread_user_interface == NULL) {
    		ast_log(LOG_ERROR, "Error checking thread's user interface status\n");
    		/* On error, assume that we are not a user interface thread */
    		return 0;
    	}
    
    	return *thread_user_interface;
    }