struct auth_client_request * auth_client_request_new(struct auth_client *client, const struct auth_request_info *request_info, auth_request_callback_t *callback, void *context) { struct auth_client_request *request; pool_t pool; pool = pool_alloconly_create("auth client request", 512); request = p_new(pool, struct auth_client_request, 1); request->pool = pool; request->conn = client->conn; request->request_info = *request_info; request->request_info.mech = p_strdup(pool, request_info->mech); request->request_info.service = p_strdup(pool, request_info->service); request->request_info.session_id = p_strdup_empty(pool, request_info->session_id); request->request_info.cert_username = p_strdup_empty(pool, request_info->cert_username); request->request_info.initial_resp_base64 = p_strdup_empty(pool, request_info->initial_resp_base64); request->callback = callback; request->context = context; request->id = auth_server_connection_add_request(request->conn, request); request->created = ioloop_time; T_BEGIN { auth_server_send_new_request(request->conn, request); } T_END; return request; }
static int acl_backend_vfile_init(struct acl_backend *_backend, const char *data) { struct acl_backend_vfile *backend = (struct acl_backend_vfile *)_backend; struct stat st; const char *const *tmp; tmp = t_strsplit(data, ":"); backend->global_path = p_strdup_empty(_backend->pool, *tmp); backend->cache_secs = ACL_VFILE_DEFAULT_CACHE_SECS; if (*tmp != NULL) tmp++; for (; *tmp != NULL; tmp++) { if (strncmp(*tmp, "cache_secs=", 11) == 0) { if (str_to_uint(*tmp + 11, &backend->cache_secs) < 0) { i_error("acl vfile: Invalid cache_secs value: %s", *tmp + 11); return -1; } } else { i_error("acl vfile: Unknown parameter: %s", *tmp); return -1; } } if (backend->global_path != NULL) { if (stat(backend->global_path, &st) < 0) { if (errno != ENOENT) { i_error("acl vfile: stat(%s) failed: %m", backend->global_path); return -1; } } else if (!S_ISDIR(st.st_mode)) { _backend->global_file = acl_global_file_init(backend->global_path, backend->cache_secs); } } if (_backend->debug) { if (backend->global_path == NULL) i_debug("acl vfile: Global ACLs disabled"); else if (_backend->global_file != NULL) { i_debug("acl vfile: Global ACL file: %s", backend->global_path); } else { i_debug("acl vfile: Global ACL legacy directory: %s", backend->global_path); } } _backend->cache = acl_cache_init(_backend, sizeof(struct acl_backend_vfile_validity)); return 0; }
struct pop3c_client * pop3c_client_init(const struct pop3c_client_settings *set) { struct pop3c_client *client; struct ssl_iostream_settings ssl_set; const char *error; pool_t pool; // CLEANUP: Remove Warning i_warning("pop3c_client_init called"); pool = pool_alloconly_create("pop3c client", 1024); client = p_new(pool, struct pop3c_client, 1); client->pool = pool; client->fd = -1; client->set.debug = set->debug; client->set.host = p_strdup(pool, set->host); client->set.port = set->port; client->set.master_user = p_strdup_empty(pool, set->master_user); client->set.username = p_strdup(pool, set->username); // CLEANUP: remove warning i_warning("pop3c_client_init: username %s", client->set.username); env_put(t_strconcat("POP3C_USERNAME="******"pop3c(%s:%u): Couldn't initialize SSL context: %s", set->host, set->port, error); } } return client; }
void auth_fields_add(struct auth_fields *fields, const char *key, const char *value, enum auth_field_flags flags) { struct auth_field *field; unsigned int idx; i_assert(*key != '\0'); i_assert(strchr(key, '\t') == NULL && strchr(key, '\n') == NULL); if (!auth_fields_find_idx(fields, key, &idx)) { if (!array_is_created(&fields->fields)) p_array_init(&fields->fields, fields->pool, 16); field = array_append_space(&fields->fields); field->key = p_strdup(fields->pool, key); } else { auth_fields_snapshot_preserve(fields); field = array_idx_modifiable(&fields->fields, idx); } field->value = p_strdup_empty(fields->pool, value); field->flags = flags | AUTH_FIELD_FLAG_CHANGED; }
struct http_client *http_client_init(const struct http_client_settings *set) { struct http_client *client; pool_t pool; pool = pool_alloconly_create("http client", 1024); client = p_new(pool, struct http_client, 1); client->pool = pool; client->set.dns_client = set->dns_client; client->set.dns_client_socket_path = p_strdup_empty(pool, set->dns_client_socket_path); client->set.user_agent = p_strdup_empty(pool, set->user_agent); client->set.rawlog_dir = p_strdup_empty(pool, set->rawlog_dir); client->set.ssl_ca_dir = p_strdup(pool, set->ssl_ca_dir); client->set.ssl_ca_file = p_strdup(pool, set->ssl_ca_file); client->set.ssl_ca = p_strdup(pool, set->ssl_ca); client->set.ssl_crypto_device = p_strdup(pool, set->ssl_crypto_device); client->set.ssl_allow_invalid_cert = set->ssl_allow_invalid_cert; client->set.ssl_cert = p_strdup(pool, set->ssl_cert); client->set.ssl_key = p_strdup(pool, set->ssl_key); client->set.ssl_key_password = p_strdup(pool, set->ssl_key_password); if (set->proxy_socket_path != NULL && *set->proxy_socket_path != '\0') { client->set.proxy_socket_path = p_strdup(pool, set->proxy_socket_path); } else if (set->proxy_url != NULL) { client->set.proxy_url = http_url_clone(pool, set->proxy_url); } client->set.proxy_username = p_strdup_empty(pool, set->proxy_username); client->set.proxy_password = p_strdup_empty(pool, set->proxy_password); client->set.max_idle_time_msecs = set->max_idle_time_msecs; client->set.max_parallel_connections = (set->max_parallel_connections > 0 ? set->max_parallel_connections : 1); client->set.max_pipelined_requests = (set->max_pipelined_requests > 0 ? set->max_pipelined_requests : 1); client->set.max_attempts = set->max_attempts; client->set.max_connect_attempts = set->max_connect_attempts; client->set.connect_backoff_time_msecs = set->connect_backoff_time_msecs == 0 ? HTTP_CLIENT_DEFAULT_BACKOFF_TIME_MSECS : set->connect_backoff_time_msecs; client->set.connect_backoff_max_time_msecs = set->connect_backoff_max_time_msecs == 0 ? HTTP_CLIENT_DEFAULT_BACKOFF_MAX_TIME_MSECS : set->connect_backoff_max_time_msecs; client->set.no_auto_redirect = set->no_auto_redirect; client->set.no_ssl_tunnel = set->no_ssl_tunnel; client->set.max_redirects = set->max_redirects; client->set.response_hdr_limits = set->response_hdr_limits; client->set.request_absolute_timeout_msecs = set->request_absolute_timeout_msecs; client->set.request_timeout_msecs = set->request_timeout_msecs; client->set.connect_timeout_msecs = set->connect_timeout_msecs; client->set.soft_connect_timeout_msecs = set->soft_connect_timeout_msecs; client->set.max_auto_retry_delay = set->max_auto_retry_delay; client->set.debug = set->debug; i_array_init(&client->delayed_failing_requests, 1); client->conn_list = http_client_connection_list_init(); hash_table_create(&client->hosts, default_pool, 0, str_hash, strcmp); hash_table_create(&client->peers, default_pool, 0, http_client_peer_addr_hash, http_client_peer_addr_cmp); return client; }
struct sieve_instance *sieve_init (const struct sieve_environment *env, const struct sieve_callbacks *callbacks, void *context, bool debug) { struct sieve_instance *svinst; const char *domain; pool_t pool; /* Create Sieve engine instance */ pool = pool_alloconly_create("sieve", 8192); svinst = p_new(pool, struct sieve_instance, 1); svinst->pool = pool; svinst->callbacks = callbacks; svinst->context = context; svinst->debug = debug; svinst->base_dir = p_strdup_empty(pool, env->base_dir); svinst->username = p_strdup_empty(pool, env->username); svinst->home_dir = p_strdup_empty(pool, env->home_dir); svinst->temp_dir = p_strdup_empty(pool, env->temp_dir); svinst->flags = env->flags; svinst->env_location = env->location; svinst->delivery_phase = env->delivery_phase; /* Determine domain */ if ( env->domainname != NULL && *(env->domainname) != '\0' ) { domain = env->domainname; } else { /* Fall back to parsing username localpart@domain */ domain = svinst->username == NULL ? NULL : strchr(svinst->username, '@'); if ( domain == NULL || *(domain+1) == '\0' ) { /* Fall back to parsing hostname host.domain */ domain = ( env->hostname != NULL ? strchr(env->hostname, '.') : NULL ); if ( domain == NULL || *(domain+1) == '\0' || strchr(domain+1, '.') == NULL ) { /* Fall back to bare hostname */ domain = env->hostname; } else { domain++; } } else { domain++; } } svinst->hostname = p_strdup_empty(pool, env->hostname); svinst->domainname = p_strdup(pool, domain); sieve_errors_init(svinst); if ( debug ) { sieve_sys_debug(svinst, "%s version %s initializing", PIGEONHOLE_NAME, PIGEONHOLE_VERSION_FULL); } /* Read configuration */ sieve_settings_load(svinst); /* Initialize extensions */ if ( !sieve_extensions_init(svinst) ) { sieve_deinit(&svinst); return NULL; } /* Initialize storage classes */ sieve_storages_init(svinst); /* Initialize plugins */ sieve_plugins_load(svinst, NULL, NULL); /* Configure extensions */ sieve_extensions_configure(svinst); return svinst; }
const char *t_strdup_empty(const char *str) { return p_strdup_empty(unsafe_data_stack_pool, str); }
static bool http_url_do_parse(struct http_url_parser *url_parser) { struct uri_parser *parser = &url_parser->parser; struct http_url *url = url_parser->url, *base = url_parser->base; const char *const *path; bool relative = TRUE, have_scheme = FALSE, have_authority = FALSE, have_path = FALSE; int path_relative; const char *part; int ret; /* RFC 7230, Appendix B: http-URI = "http://" authority path-abempty [ "?" query ] [ "#" fragment ] https-URI = "https://" authority path-abempty [ "?" query ] [ "#" fragment ] partial-URI = relative-part [ "?" query ] request-target = origin-form / absolute-form / authority-form / asterisk-form origin-form = absolute-path [ "?" query ] absolute-form = absolute-URI authority-form = authority asterisk-form = "*" ; Not parsed here absolute-path = 1*( "/" segment ) RFC 3986, Appendix A: (implemented in uri-util.h) absolute-URI = scheme ":" hier-part [ "?" query ] hier-part = "//" authority path-abempty / path-absolute / path-rootless / path-empty relative-part = "//" authority path-abempty / path-absolute / path-noscheme / path-empty authority = [ userinfo "@" ] host [ ":" port ] path-abempty = *( "/" segment ) path-absolute = "/" [ segment-nz *( "/" segment ) ] path-noscheme = segment-nz-nc *( "/" segment ) path-rootless = segment-nz *( "/" segment ) path-empty = 0<pchar> segment = *pchar segment-nz = 1*pchar segment-nz-nc = 1*( unreserved / pct-encoded / sub-delims / "@" ) ; non-zero-length segment without any colon ":" query = *( pchar / "/" / "?" ) fragment = *( pchar / "/" / "?" ) */ /* "http:" / "https:" */ if ((url_parser->flags & HTTP_URL_PARSE_SCHEME_EXTERNAL) == 0) { const char *scheme; if ((ret = uri_parse_scheme(parser, &scheme)) < 0) return FALSE; else if (ret > 0) { if (strcasecmp(scheme, "https") == 0) { if (url != NULL) url->have_ssl = TRUE; } else if (strcasecmp(scheme, "http") != 0) { if (url_parser->request_target) { /* valid as non-HTTP scheme, but also try to parse as authority */ parser->cur = parser->begin; if (!http_url_parse_authority_form(url_parser)) { url_parser->url = NULL; /* indicate non-http-url */ url_parser->req_format = HTTP_REQUEST_TARGET_FORMAT_ABSOLUTE; } return TRUE; } parser->error = "Not an HTTP URL"; return FALSE; } relative = FALSE; have_scheme = TRUE; } } else { relative = FALSE; have_scheme = TRUE; } /* "//" authority ; or * ["//"] authority ; when parsing a request target */ if (parser->cur < parser->end && parser->cur[0] == '/') { if (parser->cur+1 < parser->end && parser->cur[1] == '/') { parser->cur += 2; relative = FALSE; have_authority = TRUE; } else { /* start of absolute-path */ } } else if (url_parser->request_target && !have_scheme) { if (!http_url_parse_authority_form(url_parser)) { /* not non-HTTP scheme and invalid as authority-form */ parser->error = "Request target is invalid"; return FALSE; } return TRUE; } if (have_scheme && !have_authority) { parser->error = "Absolute HTTP URL requires `//' after `http:'"; return FALSE; } if (have_authority) { if (!http_url_parse_authority(url_parser)) return FALSE; } /* path-abempty / path-absolute / path-noscheme / path-empty */ if ((ret = uri_parse_path(parser, &path_relative, &path)) < 0) return FALSE; /* Relative URLs are only valid when we have a base URL */ if (relative) { if (base == NULL) { parser->error = "Relative HTTP URL not allowed"; return FALSE; } else if (!have_authority && url != NULL) { url->host_name = p_strdup_empty(parser->pool, base->host_name); url->host_ip = base->host_ip; url->have_host_ip = base->have_host_ip; url->port = base->port; url->have_port = base->have_port; url->have_ssl = base->have_ssl; url->user = p_strdup_empty(parser->pool, base->user); url->password = p_strdup_empty(parser->pool, base->password); } url_parser->relative = TRUE; } /* Resolve path */ if (ret > 0) { string_t *fullpath = NULL; have_path = TRUE; if (url != NULL) fullpath = t_str_new(256); if (relative && path_relative > 0 && base->path != NULL) { const char *pbegin = base->path; const char *pend = base->path + strlen(base->path); const char *p = pend - 1; i_assert(*pbegin == '/'); /* discard trailing segments of base path based on how many effective leading '..' segments were found in the relative path. */ while (path_relative > 0 && p > pbegin) { while (p > pbegin && *p != '/') p--; if (p >= pbegin) { pend = p; path_relative--; } if (p > pbegin) p--; } if (url != NULL && pend > pbegin) str_append_n(fullpath, pbegin, pend-pbegin); } /* append relative path */ while (*path != NULL) { if (!uri_data_decode(parser, *path, NULL, &part)) return FALSE; if (url != NULL) { str_append_c(fullpath, '/'); str_append(fullpath, part); } path++; } if (url != NULL) url->path = p_strdup(parser->pool, str_c(fullpath)); } else if (relative && url != NULL) { url->path = p_strdup(parser->pool, base->path); } /* [ "?" query ] */ if ((ret = uri_parse_query(parser, &part)) < 0) return FALSE; if (ret > 0) { if (!uri_data_decode(parser, part, NULL, NULL)) // check only return FALSE; if (url != NULL) url->enc_query = p_strdup(parser->pool, part); } else if (relative && !have_path && url != NULL) { url->enc_query = p_strdup(parser->pool, base->enc_query); } /* [ "#" fragment ] */ if ((ret = uri_parse_fragment(parser, &part)) < 0) return FALSE; if (ret > 0) { if ((url_parser->flags & HTTP_URL_ALLOW_FRAGMENT_PART) == 0) { parser->error = "URL fragment not allowed for HTTP URL in this context"; return FALSE; } if (!uri_data_decode(parser, part, NULL, NULL)) // check only return FALSE; if (url != NULL) url->enc_fragment = p_strdup(parser->pool, part); } else if (relative && !have_path && url != NULL) { url->enc_fragment = p_strdup(parser->pool, base->enc_fragment); } if (parser->cur != parser->end) { parser->error = "HTTP URL contains invalid character"; return FALSE; } if (have_scheme) url_parser->req_format = HTTP_REQUEST_TARGET_FORMAT_ABSOLUTE; return TRUE; }
passwd_file_add(struct passwd_file *pw, const char *username, const char *pass, const char *const *args) { /* args = uid, gid, user info, home dir, shell, extra_fields */ struct passwd_user *pu; const char *extra_fields = NULL; char *user; size_t len; if (hash_table_lookup(pw->users, username) != NULL) { i_error("passwd-file %s: User %s exists more than once", pw->path, username); return; } pu = p_new(pw->pool, struct passwd_user, 1); user = p_strdup(pw->pool, username); len = pass == NULL ? 0 : strlen(pass); if (len > 4 && pass[0] != '{' && pass[0] != '$' && pass[len-1] == ']' && pass[len-4] == '[') { /* password[type] - we're being libpam-pwdfile compatible here. it uses 13 = DES and 34 = MD5. For backwards comaptibility with ourself, we have also 56 = Digest-MD5. */ int num = (pass[len-3] - '0') * 10 + (pass[len-2] - '0'); pass = t_strndup(pass, len-4); if (num == 34) { pu->password = p_strconcat(pw->pool, "{PLAIN-MD5}", pass, NULL); } else if (num == 56) { pu->password = p_strconcat(pw->pool, "{DIGEST-MD5}", pass, NULL); if (strlen(pu->password) != 32 + 12) { i_error("passwd-file %s: User %s " "has invalid password", pw->path, username); return; } } else { pu->password = p_strconcat(pw->pool, "{CRYPT}", pass, NULL); } } else { pu->password = p_strdup(pw->pool, pass); } pu->uid = (uid_t)-1; pu->gid = (gid_t)-1; if (*args == NULL) ; else if (!pw->db->userdb || **args == '\0') { args++; } else { pu->uid = userdb_parse_uid(NULL, *args); if (pu->uid == 0 || pu->uid == (uid_t)-1) { i_error("passwd-file %s: User %s has invalid UID '%s'", pw->path, username, *args); return; } args++; } if (*args == NULL) { if (pw->db->userdb_warn_missing) { i_error("passwd-file %s: User %s is missing " "userdb info", pw->path, username); } /* don't allow userdb lookups */ pu->uid = 0; pu->gid = 0; } else if (!pw->db->userdb || **args == '\0') args++; else { pu->gid = userdb_parse_gid(NULL, *args); if (pu->gid == 0 || pu->gid == (gid_t)-1) { i_error("passwd-file %s: User %s has invalid GID '%s'", pw->path, username, *args); return; } args++; } /* user info */ if (*args != NULL) args++; /* home */ if (*args != NULL) { if (pw->db->userdb) pu->home = p_strdup_empty(pw->pool, *args); args++; } /* shell */ if (*args != NULL) args++; if (*args != NULL && **args == '\0') { /* old format, this field is empty and next field may contain MAIL */ args++; if (*args != NULL && **args != '\0' && pw->db->userdb) { extra_fields = t_strconcat("userdb_mail=", t_strarray_join(args, ":"), NULL); } } else if (*args != NULL) { /* new format, contains a space separated list of extra fields */ extra_fields = t_strarray_join(args, ":"); } if (extra_fields != NULL) { pu->extra_fields = p_strsplit_spaces(pw->pool, extra_fields, " "); } hash_table_insert(pw->users, user, pu); }
char *i_strdup_empty(const char *str) { return p_strdup_empty(default_pool, str); }