示例#1
0
/**
 * gsasl_callback:
 * @ctx: handle received from gsasl_init(), may be NULL to derive it
 *   from @sctx.
 * @sctx: session handle.
 * @prop: enumerated value of Gsasl_property type.
 *
 * Invoke the application callback.  The @prop value indicate what the
 * callback is expected to do.  For example, for
 * GSASL_ANONYMOUS_TOKEN, the function is expected to invoke
 * gsasl_property_set(SCTX, GSASL_ANONYMOUS_TOKEN, "token") where
 * "token" is the anonymous token the application wishes the SASL
 * mechanism to use.  See the manual for the meaning of all
 * parameters.
 *
 * Note that if no callback has been set by the application, but the
 * obsolete callback interface has been used, this function will
 * translate the old callback interface into the new.  This interface
 * should be sufficient to invoke all callbacks, both new and old.
 *
 * Return value: Returns whatever the application callback return, or
 *   GSASL_NO_CALLBACK if no application was known.
 *
 * Since: 0.2.0
 **/
int
gsasl_callback (Gsasl * ctx, Gsasl_session * sctx, Gsasl_property prop)
{
  if (ctx == NULL && sctx == NULL)
    return GSASL_NO_CALLBACK;

  if (ctx == NULL)
    ctx = sctx->ctx;

  if (ctx->cb)
    return ctx->cb (ctx, sctx, prop);

#ifndef GSASL_NO_OBSOLETE
  {
    /* Call obsolete callbacks.  Remove this when the obsolete
     * callbacks are no longer supported.  */
    Gsasl_server_callback_anonymous cb_anonymous;
    Gsasl_server_callback_external cb_external;
    Gsasl_server_callback_securid cb_securid;
    Gsasl_server_callback_gssapi cb_gssapi;
    Gsasl_server_callback_validate cb_validate;
    Gsasl_server_callback_retrieve cb_retrieve;
    char buf[BUFSIZ];
    size_t buflen = BUFSIZ - 1;
    int res;

    switch (prop)
      {
      case GSASL_VALIDATE_ANONYMOUS:
	if (!sctx->anonymous_token)
	  break;
	cb_anonymous = gsasl_server_callback_anonymous_get (sctx->ctx);
	if (!cb_anonymous)
	  break;
	res = cb_anonymous (sctx, sctx->anonymous_token);
	return res;
	break;

      case GSASL_VALIDATE_EXTERNAL:
	cb_external = gsasl_server_callback_external_get (sctx->ctx);
	if (!cb_external)
	  break;
	res = cb_external (sctx);
	return res;
	break;

      case GSASL_VALIDATE_SECURID:
	cb_securid = gsasl_server_callback_securid_get (sctx->ctx);
	if (!cb_securid)
	  break;
	res = cb_securid (sctx, sctx->authid, sctx->authzid, sctx->passcode,
			  sctx->pin, buf, &buflen);
	if (buflen > 0 && buflen < BUFSIZ - 1)
	  {
	    buf[buflen] = '\0';
	    gsasl_property_set (sctx, GSASL_SUGGESTED_PIN, buf);
	  }
	return res;
	break;

      case GSASL_VALIDATE_GSSAPI:
	cb_gssapi = gsasl_server_callback_gssapi_get (sctx->ctx);
	if (!cb_gssapi)
	  break;
	res = cb_gssapi (sctx, sctx->gssapi_display_name, sctx->authzid);
	return res;
	break;

      case GSASL_VALIDATE_SIMPLE:
	cb_validate = gsasl_server_callback_validate_get (sctx->ctx);
	if (!cb_validate)
	  break;
	res = cb_validate (sctx, sctx->authzid, sctx->authid, sctx->password);
	return res;
	break;

      case GSASL_PASSWORD:
	cb_retrieve = gsasl_server_callback_retrieve_get (sctx->ctx);
	if (!cb_retrieve)
	  break;
	res = cb_retrieve (sctx, sctx->authid, sctx->authzid,
			   sctx->hostname, &buf, &buflen);
	if (res == GSASL_OK)
	  gsasl_property_set_raw (sctx, GSASL_PASSWORD, buf, buflen);
	/* FIXME else if (res == GSASL_TOO_SMALL_BUFFER)... */
	return res;
	break;

      default:
	break;
      }
  }
#endif

  return GSASL_NO_CALLBACK;
}
示例#2
0
文件: gsasl.c 项目: baohaojun/dico
static int
callback(Gsasl *ctx, Gsasl_session *sctx, Gsasl_property prop)
{
    int rc = GSASL_OK;
    struct sasl_data *pdata;
    const char *user;
    char *string;

    switch (prop) {
    case GSASL_PASSWORD:
	pdata = gsasl_callback_hook_get(ctx);
	user = pdata->username;
	if (!user) {
	    user = gsasl_property_get(sctx, GSASL_AUTHID);
	    if (!user) {
		dico_log(L_ERR, 0, _("user name not supplied"));
		return GSASL_NO_AUTHID;
	    }
	    pdata->username = user;
	}
	if (dico_udb_get_password(user_db, user, &string)) {
	    dico_log(L_ERR, 0,
		     _("failed to get password for `%s' from the database"),
		     user);
	    return GSASL_NO_PASSWORD;
	} 
	gsasl_property_set(sctx, prop, string);
	free(string);
	break;

    case GSASL_SERVICE:
	gsasl_property_set(sctx, prop, sasl_service);
	break;

    case GSASL_REALM:
	gsasl_property_set(sctx, prop, sasl_realm ? sasl_realm : hostname);
	break;

    case GSASL_HOSTNAME:
	gsasl_property_set(sctx, prop, hostname);
	break;

    case GSASL_VALIDATE_SIMPLE:
	rc = cb_validate(ctx, sctx);
	break;

#if 0
    FIXME:
    case GSASL_VALIDATE_EXTERNAL:
    case GSASL_VALIDATE_SECURID:
#endif

    case GSASL_VALIDATE_ANONYMOUS:
	pdata = gsasl_callback_hook_get(ctx);
	user = gsasl_property_get(sctx, GSASL_ANONYMOUS_TOKEN);
	pdata->username = user;
	pdata->anon = 1;
	break;

    case GSASL_VALIDATE_GSSAPI:
	pdata = gsasl_callback_hook_get(ctx);
	user = gsasl_property_get(sctx, GSASL_AUTHZID);
	pdata->username = user;
	break;
	
    default:
	rc = GSASL_NO_CALLBACK;
	/*dico_log(L_NOTICE, 0, _("Unsupported callback property %d"), prop);*/
	break;
    }

    return rc;
}