/* * cyrus-sasl-extern.c - Module for Cyrus sasl external authentication. * * Copyright 2010 Ian Kent * Copyright 2010 Red Hat, Inc. * All rights reserved. * * 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, Inc., 675 Mass Ave, Cambridge MA 02139, * USA; either version 2 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. */ #include "config.h" #ifdef WITH_SASL #include #include #include #include #include #include #include #include #include "lookup_ldap.h" struct values { char *mech; char *realm; char *authcid; char *authzid; char *password; char **resps; int nresps; }; static int interaction(unsigned flags, sasl_interact_t *interact, void *values) { const char *val = interact->defresult; struct values *vals = values; switch(interact->id) { case SASL_CB_GETREALM: if (values) val = vals->realm; break; case SASL_CB_AUTHNAME: if (values) val = vals->authcid; break; case SASL_CB_PASS: if (values) val = vals->password; break; case SASL_CB_USER: if (values) val = vals->authzid; break; case SASL_CB_NOECHOPROMPT: case SASL_CB_ECHOPROMPT: break; } if (val && !*val) val = NULL; if (val || interact->id == SASL_CB_USER) { interact->result = (val && *val) ? val : ""; interact->len = strlen(interact->result); } return LDAP_SUCCESS; } int sasl_extern_interact(LDAP *ldap, unsigned flags, void *values, void *list) { sasl_interact_t *interact = list; if (!ldap) return LDAP_PARAM_ERROR; while (interact->id != SASL_CB_LIST_END) { int rc = interaction(flags, interact, values); if (rc) return rc; interact++; } return LDAP_SUCCESS; } int do_sasl_extern(LDAP *ldap, struct lookup_context *ctxt) { int flags = LDAP_SASL_QUIET; char *mech = ctxt->sasl_mech; struct values values; int rc; memset(&values, 0, sizeof(struct values)); values.mech = mech; rc = ldap_sasl_interactive_bind_s(ldap, NULL, mech, NULL, NULL, flags, sasl_extern_interact, &values); return rc; } #endif