コード例 #1
0
ファイル: tools.c プロジェクト: stewartsmith/ccan
/* Tallocs *output off ctx; return false if command fails. */
bool run_command(const void *ctx, unsigned int *time_ms, char **output,
		 const char *fmt, ...)
{
	va_list ap;
	char *cmd;
	bool ok;
	unsigned int default_time = default_timeout_ms;

	if (!time_ms)
		time_ms = &default_time;
	else if (*time_ms == 0) {
		*output = talloc_strdup(ctx, "\n== TIMED OUT ==\n");
		return false;
	}

	va_start(ap, fmt);
	cmd = talloc_vasprintf(ctx, fmt, ap);
	va_end(ap);

	*output = run_with_timeout(ctx, cmd, &ok, time_ms);
	if (ok)
		return true;
	if (!*output)
		err(1, "Problem running child");
	if (*time_ms == 0)
		*output = talloc_asprintf_append(*output,
						 "\n== TIMED OUT ==\n");
	return false;
}
コード例 #2
0
ファイル: ldb_tdb_wrap.c プロジェクト: ElijahLuk/samba
static void ltdb_log_fn(struct tdb_context *tdb, enum tdb_debug_level level, const char *fmt, ...)
{
    va_list ap;
    const char *name = tdb_name(tdb);
    struct ldb_context *ldb = talloc_get_type(tdb_get_logging_private(tdb), struct ldb_context);
    enum ldb_debug_level ldb_level;
    char *message;

    if (ldb == NULL)
        return;

    va_start(ap, fmt);
    message = talloc_vasprintf(ldb, fmt, ap);
    va_end(ap);

    switch (level) {
    case TDB_DEBUG_FATAL:
        ldb_level = LDB_DEBUG_FATAL;
        break;
    case TDB_DEBUG_ERROR:
        ldb_level = LDB_DEBUG_ERROR;
        break;
    case TDB_DEBUG_WARNING:
        ldb_level = LDB_DEBUG_WARNING;
        break;
    case TDB_DEBUG_TRACE:
        ldb_level = LDB_DEBUG_TRACE;
        break;
    default:
        ldb_level = LDB_DEBUG_FATAL;
    }

    ldb_debug(ldb, ldb_level, "ltdb: tdb(%s): %s", name, message);
    talloc_free(message);
}
コード例 #3
0
ファイル: valuepair.c プロジェクト: accense/freeradius-server
/** Add a module failure message VALUE_PAIR to the request
 */
void module_failure_msg(REQUEST *request, char const *fmt, ...)
{
	va_list ap;
	char *p;
	VALUE_PAIR *vp;

	if (!fmt || !request->packet) {
		va_start(ap, fmt);
		va_end(ap);
		return;
	}

	va_start(ap, fmt);
	vp = paircreate(request->packet, PW_MODULE_FAILURE_MESSAGE, 0);
	if (!vp) {
		va_end(ap);
		return;
	}

	p = talloc_vasprintf(vp, fmt, ap);

	if (request->module && *request->module) {
		pairsprintf(vp, "%s: %s", request->module, p);
	} else {
		pairsprintf(vp, "%s", p);
	}
	talloc_free(p);
	pairadd(&request->packet->vps, vp);
}
コード例 #4
0
/** Add a module failure message VALUE_PAIR to the request
 */
void vmodule_failure_msg(REQUEST *request, char const *fmt, va_list ap)
{
	char *p;
	VALUE_PAIR *vp;
	va_list aq;

	if (!fmt || !request->packet) {
		return;
	}

	/*
	 *  If we don't copy the original ap we get a segfault from vasprintf. This is apparently
	 *  due to ap sometimes being implemented with a stack offset which is invalidated if
	 *  ap is passed into another function. See here:
	 *  http://julipedia.meroh.net/2011/09/using-vacopy-to-safely-pass-ap.html
	 *
	 *  I don't buy that explanation, but doing a va_copy here does prevent SEGVs seen when
	 *  running unit tests which generate errors under CI.
	 */
	va_copy(aq, ap);
	p = talloc_vasprintf(request, fmt, aq);
	va_end(aq);

	MEM(vp = pairmake_packet("Module-Failure-Message", NULL, T_OP_ADD));
	if (request->module && (request->module[0] != '\0')) {
		pairsprintf(vp, "%s: %s", request->module, p);
	} else {
		pairsprintf(vp, "%s", p);
	}
	talloc_free(p);
}
コード例 #5
0
ファイル: sssd_dbus_request.c プロジェクト: celestian/sssd
static DBusError *sbus_error_new_va(TALLOC_CTX *mem_ctx,
                                    const char *error_name,
                                    const char *fmt,
                                    va_list ap)
{
    DBusError *error;
    const char *error_msg;

    error = talloc_zero(mem_ctx, DBusError);
    if (error == NULL) {
        return NULL;
    }

    if (fmt != NULL) {
        error_msg = talloc_vasprintf(error, fmt, ap);
        if (error_msg == NULL) {
            talloc_free(error);
            return NULL;
        }
    } else {
        error_msg = NULL;
    }

    dbus_error_init(error);
    dbus_set_error_const(error, error_name, error_msg);

    return error;
}
コード例 #6
0
ファイル: ctdb_io.c プロジェクト: AIdrifter/samba
/*
  setup a packet queue on a socket
 */
struct ctdb_queue *ctdb_queue_setup(struct ctdb_context *ctdb,
				    TALLOC_CTX *mem_ctx, int fd, int alignment,
				    ctdb_queue_cb_fn_t callback,
				    void *private_data, const char *fmt, ...)
{
	struct ctdb_queue *queue;
	va_list ap;

	queue = talloc_zero(mem_ctx, struct ctdb_queue);
	CTDB_NO_MEMORY_NULL(ctdb, queue);
	va_start(ap, fmt);
	queue->name = talloc_vasprintf(mem_ctx, fmt, ap);
	va_end(ap);
	CTDB_NO_MEMORY_NULL(ctdb, queue->name);

	queue->im= tevent_create_immediate(queue);
	CTDB_NO_MEMORY_NULL(ctdb, queue->im);

	queue->ctdb = ctdb;
	queue->fd = fd;
	queue->alignment = alignment;
	queue->private_data = private_data;
	queue->callback = callback;
	if (fd != -1) {
		if (ctdb_queue_set_fd(queue, fd) != 0) {
			talloc_free(queue);
			return NULL;
		}
	}
	talloc_set_destructor(queue, queue_destructor);

	return queue;
}
コード例 #7
0
ファイル: ctdb_util.c プロジェクト: jrasamba/samba
/*
  remember an error message
*/
void ctdb_set_error(struct ctdb_context *ctdb, const char *fmt, ...)
{
	va_list ap;
	talloc_free(ctdb->err_msg);
	va_start(ap, fmt);
	ctdb->err_msg = talloc_vasprintf(ctdb, fmt, ap);
	DEBUG(DEBUG_ERR,("ctdb error: %s\n", ctdb->err_msg));
	va_end(ap);
}
コード例 #8
0
ファイル: log.c プロジェクト: mcnewton/freeradius-server
/** Print errors in the TLS thread local error stack
 *
 * Drains the thread local OpenSSL error queue, and prints out the first error
 * storing it in libfreeradius's error buffer.
 *
 * @param[in] msg	Error message describing the operation being attempted.
 * @param[in] ap	Arguments for msg.
 * @return the number of errors drained from the stack.
 */
static int tls_strerror_printf_va(char const *msg, va_list ap)
{
	unsigned long	error;
	char		*p = NULL;
	int		drained = 0;
	char		buffer[256];

	int		line;
	char const	*file;
	char const	*data;
	int		flags = 0;

	/*
	 *	Pop the first error, so ERR_peek_error()
	 *	can be used to determine if there are
	 *	multiple errors.
	 */
	error = ERR_get_error_line_data(&file, &line, &data, &flags);
	if (!(flags & ERR_TXT_STRING)) data = NULL;

	if (msg) {
		/*
		 *	Print the error we were passed, and
		 *	OpenSSL's error.
		 */
		p = talloc_vasprintf(NULL, msg, ap);
		if (error) {
			ERR_error_string_n(error, buffer, sizeof(buffer));
			fr_strerror_printf("%s: %s%c%s", p, buffer, data ? ':' : '\0', data ? data : "");
			talloc_free(p);
			drained++;
		/*
		 *	Print the error we were given, irrespective
		 *	of whether there were any OpenSSL errors.
		 */
		} else {
			fr_strerror_printf("%s", p);
			talloc_free(p);
		}
	} else if (error) {
		ERR_error_string_n(error, buffer, sizeof(buffer));
		fr_strerror_printf("%s%c%s", buffer, data ? ':' : '\0', data ? data : "");
		drained++;
	} else {
		return 0;
	}

	while ((error = ERR_get_error_line_data(&file, &line, &data, &flags))) {
		if (!(flags & ERR_TXT_STRING)) data = NULL;

		ERR_error_string_n(error, buffer, sizeof(buffer));
		fr_strerror_printf_push("%s%c%s", buffer, data ? ':' : '\0', data ? data : "");
		drained++;
	}

	return drained;
}
コード例 #9
0
ファイル: talloc.c プロジェクト: jophxy/samba
/**
 * Perform string formatting, and return a pointer to newly allocated
 * memory holding the result, inside a memory pool.
 **/
 char *talloc_asprintf(TALLOC_CTX *t, const char *fmt, ...)
{
	va_list ap;
	char *ret;

	va_start(ap, fmt);
	ret = talloc_vasprintf(t, fmt, ap);
	va_end(ap);
	return ret;
}
コード例 #10
0
ファイル: dlz_bind9.c プロジェクト: rchicoli/samba
static void dlz_bind9_log_wrapper(int level, const char *fmt, ...)
{
	va_list ap;
	char *msg;
	va_start(ap, fmt);
	msg = talloc_vasprintf(NULL, fmt, ap);
	torture_comment(tctx_static, "%s\n", msg);
	TALLOC_FREE(msg);
	va_end(ap);
}
コード例 #11
0
ファイル: libnet_samsync_ldif.c プロジェクト: encukou/samba
static int fprintf_attr(FILE *add_fd, const char *attr_name,
			const char *fmt, ...)
{
	va_list ap;
	char *value, *p, *base64;
	DATA_BLOB base64_blob;
	bool do_base64 = false;
	int res;

	va_start(ap, fmt);
	value = talloc_vasprintf(NULL, fmt, ap);
	va_end(ap);

	SMB_ASSERT(value != NULL);

	for (p=value; *p; p++) {
		if (*p & 0x80) {
			do_base64 = true;
			break;
		}
	}

	if (!do_base64) {
		bool only_whitespace = true;
		for (p=value; *p; p++) {
			/*
			 * I know that this not multibyte safe, but we break
			 * on the first non-whitespace character anyway.
			 */
			if (!isspace(*p)) {
				only_whitespace = false;
				break;
			}
		}
		if (only_whitespace) {
			do_base64 = true;
		}
	}

	if (!do_base64) {
		res = fprintf(add_fd, "%s: %s\n", attr_name, value);
		TALLOC_FREE(value);
		return res;
	}

	base64_blob.data = (unsigned char *)value;
	base64_blob.length = strlen(value);

	base64 = base64_encode_data_blob(value, base64_blob);
	SMB_ASSERT(base64 != NULL);

	res = fprintf(add_fd, "%s:: %s\n", attr_name, base64);
	TALLOC_FREE(value);
	return res;
}
コード例 #12
0
ファイル: nc-scr.c プロジェクト: johnhihi/petitboot
void nc_scr_status_printf(struct nc_scr *scr, const char *format, ...)
{
	va_list ap;

	nc_scr_status_free(scr);

	va_start(ap, format);
	scr->frame.status = talloc_vasprintf(scr, format, ap);
	va_end(ap);

	nc_scr_status_draw(scr);
	wrefresh(scr->main_ncw);
}
コード例 #13
0
ファイル: ctdb_fork.c プロジェクト: Gazzonyx/samba
void ctdb_set_child_info(TALLOC_CTX *mem_ctx, const char *child_name_fmt, ...)
{
	if (child_name_fmt != NULL) {
		va_list ap;
		char *t;

		va_start(ap, child_name_fmt);
		t = talloc_vasprintf(mem_ctx, child_name_fmt, ap);
		debug_extra = talloc_asprintf(mem_ctx, "%s:", t);
		talloc_free(t);
		va_end(ap);
	}
}
コード例 #14
0
ファイル: ldb_debug.c プロジェクト: gojdic/samba
/*
  log a message, and set the ldb error string to the same message
*/
void ldb_debug_set(struct ldb_context *ldb, enum ldb_debug_level level, 
		   const char *fmt, ...)
{
	va_list ap;
	char *msg;
	va_start(ap, fmt);
	msg = talloc_vasprintf(ldb, fmt, ap);
	va_end(ap);
	if (msg != NULL) {
		ldb_set_errstring(ldb, msg);
		ldb_debug(ldb, level, "%s", msg);
	}
	talloc_free(msg);
}
コード例 #15
0
ファイル: talloc.c プロジェクト: jophxy/samba
/**
 * Create a new talloc context, with a name specifying its purpose.
 * Please call this in preference to talloc_init().
 **/
 TALLOC_CTX *talloc_init_named(char const *fmt, ...) 
{
	TALLOC_CTX *t;
	va_list ap;

	t = talloc_init();
	if (t && fmt) {
		va_start(ap, fmt);
		t->name = talloc_vasprintf(t, fmt, ap);
		va_end(ap);
	}
	
	return t;
}
コード例 #16
0
ファイル: util_ldb.c プロジェクト: gojdic/samba
/*
  search the sam for the specified attributes - va_list variant
*/
int gendb_search_v(struct ldb_context *ldb,
		   TALLOC_CTX *mem_ctx,
		   struct ldb_dn *basedn,
		   struct ldb_message ***msgs,
		   const char * const *attrs,
		   const char *format,
		   va_list ap) 
{
	enum ldb_scope scope = LDB_SCOPE_SUBTREE;
	struct ldb_result *res;
	char *expr = NULL;
	int ret;

	if (format) {
		expr = talloc_vasprintf(mem_ctx, format, ap);
		if (expr == NULL) {
			return -1;
		}
	} else {
		scope = LDB_SCOPE_BASE;
	}

	res = NULL;

	ret = ldb_search(ldb, mem_ctx, &res, basedn, scope, attrs,
			 expr?"%s":NULL, expr);

	if (ret == LDB_SUCCESS) {
		talloc_steal(mem_ctx, res->msgs);

		DEBUG(6,("gendb_search_v: %s %s -> %d\n",
			 basedn?ldb_dn_get_linearized(basedn):"NULL",
			 expr?expr:"NULL", res->count));

		ret = res->count;
		*msgs = res->msgs;
		talloc_free(res);
	} else if (scope == LDB_SCOPE_BASE && ret == LDB_ERR_NO_SUCH_OBJECT) {
		ret = 0;
		*msgs = NULL;
	} else {
		DEBUG(4,("gendb_search_v: search failed: %s\n",
					ldb_errstring(ldb)));
		ret = -1;
	}

	talloc_free(expr);

	return ret;
}
コード例 #17
0
ファイル: torture.c プロジェクト: gojdic/samba
/**
 * Comment on the status/progress of a test
 */
void torture_comment(struct torture_context *context, const char *comment, ...)
{
	va_list ap;
	char *tmp;

	if (!context->results->ui_ops->comment)
		return;

	va_start(ap, comment);
	tmp = talloc_vasprintf(context, comment, ap);
		
	context->results->ui_ops->comment(context, tmp);
	
	talloc_free(tmp);
}
コード例 #18
0
ファイル: torture.c プロジェクト: gojdic/samba
/**
 * Store the result of a torture test.
 */
void torture_result(struct torture_context *context, 
		    enum torture_result result, const char *fmt, ...)
{
	va_list ap;

	va_start(ap, fmt);

	if (context->last_reason) {
		torture_warning(context, "%s", context->last_reason);
		talloc_free(context->last_reason);
	}

	context->last_result = result;
	context->last_reason = talloc_vasprintf(context, fmt, ap);
	va_end(ap);
}
コード例 #19
0
ファイル: netapi.c プロジェクト: gojdic/samba
NET_API_STATUS libnetapi_set_error_string(struct libnetapi_ctx *ctx,
					  const char *format, ...)
{
	va_list args;

	TALLOC_FREE(ctx->error_string);

	va_start(args, format);
	ctx->error_string = talloc_vasprintf(ctx, format, args);
	va_end(args);

	if (!ctx->error_string) {
		return W_ERROR_V(WERR_NOMEM);
	}
	return NET_API_STATUS_SUCCESS;
}
コード例 #20
0
ファイル: ldb_msg.c プロジェクト: Alexander--/samba
/*
  add a printf formatted element to a message
*/
int ldb_msg_add_fmt(struct ldb_message *msg,
		    const char *attr_name, const char *fmt, ...)
{
	struct ldb_val val;
	va_list ap;
	char *str;

	va_start(ap, fmt);
	str = talloc_vasprintf(msg, fmt, ap);
	va_end(ap);

	if (str == NULL) return LDB_ERR_OPERATIONS_ERROR;

	val.data   = (uint8_t *)str;
	val.length = strlen(str);

	return ldb_msg_add_steal_value(msg, attr_name, &val);
}
コード例 #21
0
ファイル: boot.c プロジェクト: johnhihi/petitboot
static void __attribute__((format(__printf__, 4, 5))) update_status(
		boot_status_fn fn, void *arg, int type, char *fmt, ...)
{
	struct boot_status status;
	va_list ap;

	va_start(ap, fmt);
	status.message = talloc_vasprintf(NULL, fmt, ap);
	va_end(ap);

	status.type = type;
	status.progress = -1;
	status.detail = NULL;

	pb_debug("boot status: [%d] %s\n", type, status.message);

	fn(arg, &status);

	talloc_free(status.message);
}
コード例 #22
0
ファイル: ctdb_io.c プロジェクト: urisimchoni/samba
/*
  setup a packet queue on a socket
 */
struct ctdb_queue *ctdb_queue_setup(struct ctdb_context *ctdb,
				    TALLOC_CTX *mem_ctx, int fd, int alignment,
				    ctdb_queue_cb_fn_t callback,
				    void *private_data, const char *fmt, ...)
{
	struct ctdb_queue *queue;
	va_list ap;

	queue = talloc_zero(mem_ctx, struct ctdb_queue);
	CTDB_NO_MEMORY_NULL(ctdb, queue);
	va_start(ap, fmt);
	queue->name = talloc_vasprintf(mem_ctx, fmt, ap);
	va_end(ap);
	CTDB_NO_MEMORY_NULL(ctdb, queue->name);

	queue->im= tevent_create_immediate(queue);
	CTDB_NO_MEMORY_NULL(ctdb, queue->im);

	queue->ctdb = ctdb;
	queue->fd = fd;
	queue->alignment = alignment;
	queue->private_data = private_data;
	queue->callback = callback;
	if (fd != -1) {
		if (ctdb_queue_set_fd(queue, fd) != 0) {
			talloc_free(queue);
			return NULL;
		}
	}
	talloc_set_destructor(queue, queue_destructor);

	queue->buffer_size = ctdb->tunable.queue_buffer_size;
	/* In client code, ctdb->tunable is not initialized.
	 * This does not affect recovery daemon.
	 */
	if (queue->buffer_size == 0) {
		queue->buffer_size = 1024;
	}

	return queue;
}
コード例 #23
0
ファイル: ctdb_call.c プロジェクト: technosaurus/samba4-GPL2
static void ctdb_send_error(struct ctdb_context *ctdb, 
			    struct ctdb_req_header *hdr, uint32_t status,
			    const char *fmt, ...)
{
	va_list ap;
	struct ctdb_reply_error *r;
	char *msg;
	int msglen, len;

	va_start(ap, fmt);
	msg = talloc_vasprintf(ctdb, fmt, ap);
	if (msg == NULL) {
		ctdb_fatal(ctdb, "Unable to allocate error in ctdb_send_error\n");
	}
	va_end(ap);

	msglen = strlen(msg)+1;
	len = offsetof(struct ctdb_reply_error, msg);
	r = ctdb->methods->allocate_pkt(msg, len + msglen);
	CTDB_NO_MEMORY_FATAL(ctdb, r);
	talloc_set_name_const(r, "send_error packet");

	r->hdr.length    = len + msglen;
	r->hdr.ctdb_magic = CTDB_MAGIC;
	r->hdr.ctdb_version = CTDB_VERSION;
	r->hdr.operation = CTDB_REPLY_ERROR;
	r->hdr.destnode  = hdr->srcnode;
	r->hdr.srcnode   = ctdb->vnn;
	r->hdr.reqid     = hdr->reqid;
	r->status        = status;
	r->msglen        = msglen;
	memcpy(&r->msg[0], msg, msglen);

	ctdb_queue_packet(ctdb, &r->hdr);

	talloc_free(msg);
}
コード例 #24
0
ファイル: valuepair.c プロジェクト: kcnwogu/freeradius-server
/** Add a module failure message VALUE_PAIR to the request
 */
void vmodule_failure_msg(REQUEST *request, char const *fmt, va_list ap)
{
	char *p;
	VALUE_PAIR *vp;
	va_list aq;

	if (!fmt || !request->packet) {
		return;
	}

	vp = paircreate(request->packet, PW_MODULE_FAILURE_MESSAGE, 0);
	if (!vp) {
		return;
	}

	/*
	 *  If we don't copy the original ap we get a segfault from vasprintf. This is apparently
	 *  due to ap sometimes being implemented with a stack offset which is invalidated if
	 *  ap is passed into another function. See here:
	 *  http://julipedia.meroh.net/2011/09/using-vacopy-to-safely-pass-ap.html
	 *
	 *  I don't buy that explanation, but doing a va_copy here does prevent SEGVs seen when
	 *  running unit tests which generate errors under CI.
	 */
	va_copy(aq, ap);
	p = talloc_vasprintf(vp, fmt, aq);
	talloc_set_type(p, char);
	va_end(aq);
	if (request->module && *request->module) {
		pairsprintf(vp, "%s: %s", request->module, p);
	} else {
		pairsprintf(vp, "%s", p);
	}
	talloc_free(p);
	pairadd(&request->packet->vps, vp);
}
コード例 #25
0
ファイル: log.c プロジェクト: mcnewton/freeradius-server
/** Print errors in the TLS thread local error stack
 *
 * Drains the thread local OpenSSL error queue, and prints out errors.
 *
 * @param[in] request	The current request (may be NULL).
 * @param[in] msg	Error message describing the operation being attempted.
 * @param[in] ap	Arguments for msg.
 * @return the number of errors drained from the stack.
 */
static int tls_log_error_va(REQUEST *request, char const *msg, va_list ap)
{
	unsigned long	error;
	char		*p;
	int		in_stack = 0;
	char		buffer[256];

	int		line;
	char const	*file;
	char const	*data;
	int		flags = 0;

	/*
	 *	Pop the first error, so ERR_peek_error()
	 *	can be used to determine if there are
	 *	multiple errors.
	 */
	error = ERR_get_error_line_data(&file, &line, &data, &flags);
	if (!(flags & ERR_TXT_STRING)) data = NULL;

	if (msg) {
		p = talloc_vasprintf(request, msg, ap);

		/*
		 *	Single line mode (there's only one error)
		 */
		if (error && !ERR_peek_error()) {
			ERR_error_string_n(error, buffer, sizeof(buffer));

			/* Extra verbose */
			if ((request && RDEBUG_ENABLED3) || DEBUG_ENABLED3) {
				ROPTIONAL(REDEBUG, ERROR, "%s: %s[%i]:%s%c%s", p, file, line, buffer,
					  data ? ':' : '\0', data ? data : "");
			} else {
				ROPTIONAL(REDEBUG, ERROR, "%s: %s%c%s", p, buffer,
					  data ? ':' : '\0', data ? data : "");
			}

			talloc_free(p);

			return 1;
		}

		/*
		 *	Print the error we were given, irrespective
		 *	of whether there were any OpenSSL errors.
		 */
		ROPTIONAL(RERROR, ERROR, "%s", p);
		talloc_free(p);
	}

	/*
	 *	Stack mode (there are multiple errors)
	 */
	if (!error) return 0;
	do {
		if (!(flags & ERR_TXT_STRING)) data = NULL;

		ERR_error_string_n(error, buffer, sizeof(buffer));
		/* Extra verbose */
		if ((request && RDEBUG_ENABLED3) || DEBUG_ENABLED3) {
			ROPTIONAL(REDEBUG, ERROR, "%s[%i]:%s%c%s", file, line, buffer,
				  data ? ':' : '\0', data ? data : "");
		} else {
			ROPTIONAL(REDEBUG, ERROR, "%s%c%s", buffer,
				  data ? ':' : '\0', data ? data : "");
		}
		in_stack++;
	} while ((error = ERR_get_error_line_data(&file, &line, &data, &flags)));

	return in_stack;
}
コード例 #26
0
ファイル: util.c プロジェクト: endisd/samba
		       struct ldb_dn *basedn, enum ldb_scope scope, 
		       const char * const *attrs,
		       int dsdb_flags, 
		       const char *format, ...) _PRINTF_ATTRIBUTE(8, 9)
{
	int ret;
	struct ldb_request *req;
	TALLOC_CTX *tmp_ctx;
	struct ldb_result *res;
	va_list ap;
	char *expression;

	tmp_ctx = talloc_new(mem_ctx);

	va_start(ap, format);
	expression = talloc_vasprintf(tmp_ctx, format, ap);
	va_end(ap);

	res = talloc_zero(tmp_ctx, struct ldb_result);
	if (!res) {
		return LDB_ERR_OPERATIONS_ERROR;
	}

	ret = ldb_build_search_req(&req, ldb_module_get_ctx(module), tmp_ctx,
				   basedn,
				   scope,
				   expression,
				   attrs,
				   NULL,
				   res,
				   ldb_search_default_callback,