DAEMONOBJ:=renewd.o renew.o common.o commands.o api.o voms.o
LIBOBJ:=api.o common.o
+LIB_CORE_OBJS := renewal_core.o voms.o renewal_core_compat.o
CLIENTOBJ:=client.o
THRLIBOBJ:=${LIBOBJ:.o=.thr.o}
LIBLOBJ:=${LIBOBJ:.o=.lo}
THRLIBLOBJ:=${LIBOBJ:.o=.thr.lo}
+LIB_CORE_NOTHR_OBJS := ${LIB_CORE_OBJS}
+LIB_CORE_NOTHR_LOBJS := ${LIB_CORE_OBJS:.o=.lo}
+LIB_CORE_THR_OBJS := ${LIB_CORE_OBJS:.o=.thr.o}
+LIB_CORE_THR_LOBJS := ${LIB_CORE_OBJS:.o=.thr.lo}
+
LIB:=libglite_security_proxyrenewal_${nothrflavour}.la
THRLIB:=libglite_security_proxyrenewal_${thrflavour}.la
+LIB_CORE_NOTHR := libglite_security_proxyrenewal_core_${nothrflavour}.la
+LIB_CORE_THR := libglite_security_proxyrenewal_core_${thrflavour}.la
DAEMON:=glite-proxy-renewd
CLIENT:=glite-proxy-renew
default: all
-compile all: ${LIB} ${THRLIB} ${DAEMON} ${CLIENT}
+compile all: ${LIB} ${THRLIB} ${LIB_CORE_NOTHR} ${DAEMON} ${CLIENT}
${LIB}: ${LIBOBJ}
${LINK} -o $@ ${LIBLOBJ} -rpath ${glite_location}/lib ${JOBIDLIB}
${THRLIB}: ${THRLIBOBJ}
${LINK} -o $@ ${THRLIBLOBJ} -rpath ${glite_location}/lib
+${LIB_CORE_NOTHR}: ${LIB_CORE_NOTHR_OBJS}
+ ${LINK} -o $@ ${LIB_CORE_NOTHR_OBJS} -rpath ${glite_location}/lib ${MYPROXY_LIB} -L${glite_location}/lib -lvomsc_${nothrflavour}
+
${DAEMON}: ${DAEMONOBJ}
${LINK} -o $@ ${DAEMONOBJ} ${JOBIDLIB} ${MYPROXY_LIB} -lvomsc -lglobus_gss_assist_${nothrflavour} ${GLOBUS_LIBS}
${CLIENT}: ${CLIENTOBJ} ${LIB}
${LINK} -o $@ ${CLIENTOBJ} ${LIB} ${GLOBUS_LIBS}
-${THRLIBOBJ}: %.thr.o: %.c
+${THRLIBOBJ} ${LIB_CORE_THR_OBJS}: %.thr.o: %.c
${COMPILE} ${GLOBUSTHRINC} -o $@ -c $<
%.o: %.c
install:
-mkdir -p ${PREFIX}/bin ${PREFIX}/lib ${PREFIX}/include/glite/security/proxyrenewal ${PREFIX}/share/doc/${package}-${version} ${PREFIX}/etc/init.d
- ${INSTALL} -m 644 ${LIB} ${THRLIB} ${PREFIX}/lib
+ ${INSTALL} -m 644 ${LIB} ${THRLIB} ${LIB_CORE_NOTHR} ${PREFIX}/lib
${INSTALL} -m 755 ${DAEMON} ${CLIENT} ${PREFIX}/bin
${INSTALL} -m 644 ${top_srcdir}/LICENSE ${PREFIX}/share/doc/${package}-${version}
- cd ${top_srcdir}/interface && ${INSTALL} -m 644 renewal.h ${PREFIX}/include/glite/security/proxyrenewal
+ cd ${top_srcdir}/interface && ${INSTALL} -m 644 renewal.h renewal_core.h ${PREFIX}/include/glite/security/proxyrenewal
${INSTALL} -m 755 ${top_srcdir}/config/startup ${PREFIX}/etc/init.d/glite-proxy-renewald
clean:
- $(RM) $(LIB) $(DAEMON) $(CLIENT) *.o core
+ $(RM) $(LIB) ${LIB_CORE_NOTHR} $(DAEMON) $(CLIENT) *.o core
--- /dev/null
+#ifndef RENEWAL_CORE_H
+#define RENEWAL_CORE_H
+
+#ident "$Id$"
+
+#include <sys/syslog.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+typedef enum {
+ GLITE_RENEWAL_LOG_NONE,
+ GLITE_RENEWAL_LOG_STDOUT,
+ GLITE_RENEWAL_LOG_SYSLOG,
+} glite_renewal_log_dst;
+
+typedef struct glite_renewal_core_context_data {
+ int log_level;
+ glite_renewal_log_dst log_dst;
+ char *err_message;
+ char *voms_conf;
+} glite_renewal_core_context_data;
+
+typedef struct glite_renewal_core_context_data *glite_renewal_core_context;
+
+/**
+ * This cal initializes the context and sets default values
+ */
+int
+glite_renewal_core_init_ctx(glite_renewal_core_context *context);
+
+/**
+ * This call frees the context and all memory used by the context
+ */
+int
+glite_renewal_core_destroy_ctx(glite_renewal_core_context context);
+
+/**
+ * This call tries to renew the proxy certificate using the MyProxy
+ * repository. If VOMS attributes are present in the proxy they are renewed
+ * as well.
+ * \param context IN: context with authentication information
+ * \param myproxy_server IN: hostname of the myproxy repository
+ * \param myproxy_port IN: TCP port of the myproxy repository, if 0 the
+ * default value will be used
+ * \param current_proxy IN: filename with the proxy to renew
+ * \param new_proxy OUT: filename with the renewed proxy, the caller is
+ * responsible for removing the file when it's not needed.
+ */
+int
+glite_renewal_core_renew(glite_renewal_core_context context,
+ const char *myproxy_server,
+ unsigned int myproxy_port,
+ const char *current_proxy,
+ char **new_proxy);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* RENEWAL_CORE_H */
--- /dev/null
+#include <myproxy.h>
+#include <myproxy_delegation.h>
+
+#include "renewal_core.h"
+#include "renewal_locl.h"
+#include "renewd_locl.h"
+
+static const char rcsid[] = "$Id$";
+
+int
+glite_renewal_load_proxy(glite_renewal_core_context ctx, const char *cur_file, X509 **cert, EVP_PKEY **priv_key,
+ STACK_OF(X509) **chain, globus_gsi_cred_handle_t *cur_proxy)
+{
+ globus_result_t result;
+ globus_gsi_cred_handle_t proxy = NULL;
+ int ret;
+
+ result = globus_gsi_cred_handle_init(&proxy, NULL);
+ if (result) {
+ fprintf(stderr, "globus_gsi_cred_handle_init() failed\n");
+ goto end;
+ }
+
+ result = globus_gsi_cred_read_proxy(proxy, (char *) cur_file);
+ if (result) {
+ fprintf(stderr, "globus_gsi_cred_read_proxy() failed\n");
+ goto end;
+ }
+
+ if (cert) {
+ result = globus_gsi_cred_get_cert(proxy, cert);
+ if (result) {
+ fprintf(stderr, "globus_gsi_cred_get_cert() failed\n");
+ goto end;
+ }
+ }
+
+ if (priv_key) {
+ result = globus_gsi_cred_get_key(proxy, priv_key);
+ if (result) {
+ fprintf(stderr, "globus_gsi_cred_get_key() failed\n");
+ goto end;
+ }
+ }
+
+ if (chain) {
+ result = globus_gsi_cred_get_cert_chain(proxy, chain);
+ if (result) {
+ fprintf(stderr, "globus_gsi_cred_get_cert_chain() failed\n");
+ goto end;
+ }
+ }
+
+ if (cur_proxy) {
+ *cur_proxy = proxy;
+ proxy = NULL;
+ }
+
+ ret = 0;
+
+end:
+ if (proxy)
+ globus_gsi_cred_handle_destroy(proxy);
+ if (result)
+ ret = EDG_WLPR_ERROR_GENERIC;
+
+ return ret;
+}
+
+int
+glite_renewal_get_proxy_base_name(glite_renewal_core_context ctx, const char *file, char **name)
+{
+ X509 *cert = NULL;
+ EVP_PKEY *key = NULL;
+ STACK_OF(X509) *chain = NULL;
+ X509_NAME *subject = NULL;
+ int ret;
+ globus_result_t result;
+
+ ret = glite_renewal_load_proxy(ctx, file, &cert, &key, &chain, NULL);
+ if (ret)
+ return ret;
+
+ subject = X509_NAME_dup(X509_get_subject_name(cert));
+
+ sk_X509_insert(chain, cert, 0);
+ cert = NULL;
+
+ result = globus_gsi_cert_utils_get_base_name(subject, chain);
+ if (result) {
+ glite_renewal_log(ctx, LOG_ERR, "Cannot get subject name from proxy %s", file);
+ ret = EDG_WLPR_ERROR_SSL; /* XXX ??? */
+ goto end;
+ }
+
+ *name = X509_NAME_oneline(subject, NULL, 0);
+ ret = 0;
+
+end:
+ if (cert)
+ X509_free(cert);
+ if (key)
+ EVP_PKEY_free(key);
+ if (chain)
+ sk_X509_pop_free(chain, X509_free);
+ if (subject)
+ X509_NAME_free(subject);
+
+ return ret;
+}
+
+int
+glite_renewal_core_renew(glite_renewal_core_context ctx,
+ const char * myproxy_server,
+ unsigned int myproxy_port,
+ const char *current_proxy,
+ char **new_proxy)
+{
+ char tmp_proxy[FILENAME_MAX];
+ int tmp_fd;
+ int ret = -1;
+ char *p;
+ const char *server = NULL;
+ myproxy_socket_attrs_t *socket_attrs;
+ myproxy_request_t *client_request;
+ myproxy_response_t *server_response;
+ char *renewed_proxy;
+ int voms_exts;
+
+ socket_attrs = malloc(sizeof(*socket_attrs));
+ memset(socket_attrs, 0, sizeof(*socket_attrs));
+
+ client_request = malloc(sizeof(*client_request));
+ memset(client_request, 0, sizeof(*client_request));
+
+ server_response = malloc(sizeof(*server_response));
+ memset(server_response, 0, sizeof(*server_response));
+
+ myproxy_set_delegation_defaults(socket_attrs, client_request);
+
+ glite_renewal_log(ctx, LOG_DEBUG, "Trying to renew proxy in %s", current_proxy);
+
+ snprintf(tmp_proxy, sizeof(tmp_proxy), "%s.myproxy.XXXXXX", current_proxy);
+ tmp_fd = mkstemp(tmp_proxy);
+ if (tmp_fd == -1) {
+ glite_renewal_log(ctx, LOG_ERR, "Cannot create temporary file (%s)",
+ strerror(errno));
+ return errno;
+ }
+
+ ret = glite_renewal_get_proxy_base_name(ctx, current_proxy, &client_request->username);
+ if (ret)
+ goto end;
+
+ voms_exts = glite_renewal_check_voms_attrs(ctx, current_proxy);
+
+ client_request->proxy_lifetime = 60 * 60 * DGPR_RETRIEVE_DEFAULT_HOURS;
+
+ server = (myproxy_server) ? myproxy_server : socket_attrs->pshost;
+ if (server == NULL) {
+ glite_renewal_log(ctx, LOG_ERR, "No myproxy server specified");
+ ret = EINVAL;
+ goto end;
+ }
+ socket_attrs->pshost = strdup(server);
+
+ socket_attrs->psport = (myproxy_port) ? myproxy_port : MYPROXY_SERVER_PORT;
+
+ verror_clear();
+ ret = myproxy_get_delegation(socket_attrs, client_request, (char *) current_proxy,
+ server_response, tmp_proxy);
+ if (ret == 1) {
+ ret = EDG_WLPR_ERROR_MYPROXY;
+ glite_renewal_log(ctx, LOG_ERR, "Error contacting MyProxy server for proxy %s: %s",
+ current_proxy, verror_get_string());
+ verror_clear();
+ goto end;
+ }
+
+ renewed_proxy = tmp_proxy;
+
+ if (voms_exts) {
+ char tmp_voms_proxy[FILENAME_MAX];
+ int tmp_voms_fd;
+
+ snprintf(tmp_voms_proxy, sizeof(tmp_voms_proxy), "%s.voms.XXXXXX",
+ current_proxy);
+ tmp_voms_fd = mkstemp(tmp_voms_proxy);
+ if (tmp_voms_fd == -1) {
+ glite_renewal_log(ctx, LOG_ERR, "Cannot create temporary file (%s)",
+ strerror(errno));
+ ret = errno;
+ goto end;
+ }
+
+ ret = glite_renewal_renew_voms_creds(ctx, current_proxy, renewed_proxy, tmp_voms_proxy);
+ close(tmp_voms_fd);
+ if (ret) {
+ unlink(tmp_voms_proxy);
+ goto end;
+ }
+
+ renewed_proxy = tmp_voms_proxy;
+ unlink(tmp_proxy);
+ }
+
+ if (new_proxy)
+ *new_proxy = strdup(renewed_proxy);
+
+ ret = 0;
+
+end:
+ if (socket_attrs->socket_fd)
+ close(socket_attrs->socket_fd);
+ close(tmp_fd);
+ if (ret)
+ unlink(tmp_proxy);
+ myproxy_free(socket_attrs, client_request, server_response);
+
+ return ret;
+}
+
+int
+glite_renewal_core_init_ctx(glite_renewal_core_context *context)
+{
+ glite_renewal_core_context p = NULL;
+
+ *context = NULL;
+
+ p = calloc(1, sizeof(*p));
+ if (p == NULL)
+ return ENOMEM;
+
+ p->log_level = LOG_ERR;
+ p->log_dst = GLITE_RENEWAL_LOG_SYSLOG;
+
+ *context = p;
+ return 0;
+}
+
+int
+glite_renewal_core_destroy_ctx(glite_renewal_core_context context)
+{
+ if (context == NULL)
+ return 0;
+ if (context->err_message);
+ free(context->err_message);
+ free(context);
+ return 0;
+}
+
+void
+glite_renewal_log(glite_renewal_core_context context, int dbg_level, const char *format, ...)
+{
+ va_list ap;
+
+ if (context->err_message) {
+ free(context->err_message);
+ context->err_message = NULL;
+ }
+
+ /* cannot handle the %m format argument specific for syslog() */
+ va_start(ap, format);
+ vasprintf(&context->err_message, format, ap);
+ va_end(ap);
+
+ if (dbg_level > context->log_level)
+ return;
+
+ switch (context->log_dst) {
+ case GLITE_RENEWAL_LOG_STDOUT:
+ printf("%s\n", context->err_message);
+ break;
+ case GLITE_RENEWAL_LOG_SYSLOG:
+ syslog(dbg_level, "%s", context->err_message);
+ break;
+ case GLITE_RENEWAL_LOG_NONE:
+ default:
+ break;
+ }
+
+ return;
+}
--- /dev/null
+/*
+ * This is a "glue" file containing various pieces that are needed to build
+ * separated renewal_core library.
+ */
+
+#include <glite/security/voms/voms_apic.h>
+
+#include "renewal_core.h"
+#include "renewal_locl.h"
+#include "renewd_locl.h"
+
+char *vomsconf = NULL;
+static glite_renewal_core_context saved_ctx = NULL;
+
+/* Wrapper calling renew_voms_creds() from voms.o */
+int
+glite_renewal_renew_voms_creds(glite_renewal_core_context ctx, const char *cur_file, const char *renewed_file, const char *new_file)
+{
+ int ret;
+
+ vomsconf = ctx->voms_conf;
+ saved_ctx = ctx;
+ ret = renew_voms_creds(cur_file, renewed_file, new_file);
+ saved_ctx = NULL;
+
+ return ret;
+}
+
+/* This is called from voms.o, normaly it sits in renew.o, which we don't want
+ * to add to the renewal_core lib. */
+int
+load_proxy(const char *cur_file, X509 **cert, EVP_PKEY **priv_key,
+ STACK_OF(X509) **chain, globus_gsi_cred_handle_t *cur_proxy)
+{
+ assert(saved_ctx != NULL);
+
+ return glite_renewal_load_proxy(saved_ctx, cur_file, cert, priv_key, chain, cur_proxy);
+}
+
+/* This is called from voms.o */
+void
+edg_wlpr_Log(int dbg_level, const char *format, ...)
+{
+ char *str;
+ va_list ap;
+
+ assert(saved_ctx != NULL);
+
+ va_start(ap, format);
+ vasprintf(&str, format, ap);
+ va_end(ap);
+
+ glite_renewal_log(saved_ctx, dbg_level, "%s", str);
+ free(str);
+}
+
+/* A new call not implemented in 3.0 version of voms.o */
+int
+glite_renewal_check_voms_attrs(glite_renewal_core_context ctx, const char *proxy)
+{
+ int ret, voms_err, present;
+ X509 *cert = NULL;
+ STACK_OF(X509) *chain = NULL;
+ struct vomsdata *vd = NULL;
+
+ ret = glite_renewal_load_proxy(ctx, proxy, &cert, NULL, &chain, NULL);
+ if (ret)
+ return 0;
+
+ vd = VOMS_Init(NULL, NULL);
+ if (vd == NULL) {
+ present = 0;
+ goto end;
+ }
+
+ ret = VOMS_Retrieve(cert, chain, RECURSE_CHAIN, vd, &voms_err);
+ if (ret == 0) {
+ present = 0;
+ goto end;
+ }
+
+ present = 1;
+
+end:
+ if (cert)
+ X509_free(cert);
+ if (chain)
+ sk_X509_pop_free(chain, X509_free);
+ if (vd)
+ VOMS_Destroy(vd);
+
+ return present;
+}