Commits

Anonymous committed b6d0227

Support libassuan-2.0.

Comments (0)

Files changed (3)

 OBJS = mirage-getopt.o mirage-wrapper.o mirage-password.o
 
 CONFIGTESTS = check-getopt.o check-sysexits.o check-mmapio.o check-termios.o $(ASSUAN_CHECK)
-CONFIGIN = check-getopt.c check-sysexits.c check-mmapio.c check-termios.c check-assuan.c
-CONFIGCLEANADD = check-assuan
+CONFIGIN = check-getopt.c check-sysexits.c check-mmapio.c check-termios.c check-assuan.c check-assuan2.c
+CONFIGCLEANADD = check-assuan check-assuan2
 
 DESTDIR = 
 
 	printf '#define _POSIX_C_SOURCE 200112L\n#include <stdio.h>\n#include <termios.h>\n#include <unistd.h>\nint main(void) { struct termios term; return tcgetattr(fileno(stdin), &term); }\n' > $@
 
 check-assuan.c:
-	printf '#define _ISO_C99_SOURCE 1\n#include <assuan.h>\nint main(void) { assuan_context_t ctx; return assuan_pipe_connect(&ctx, "/bin/true", 0, 0); }\n' > $@
+	printf '#define _ISO_C99_SOURCE 1\n#include <assuan.h>\nint main(void) { assuan_context_t ctx; assuan_error_t ret = assuan_pipe_connect(&ctx, "/bin/true", 0, 0); assuan_disconnect(ctx); return ret; }\n' > $@
+
+check-assuan2.c:
+	printf '#define _ISO_C99_SOURCE 1\n#include <gpg-error.h>\n#include <assuan.h>\nint main(void) { assuan_context_t ctx; assuan_new(&ctx); gpg_error_t ret = assuan_pipe_connect(ctx, "/bin/true", 0, 0, 0, 0, 0); assuan_release(ctx); return ret; }\n' > $@
 
 check-assuan: check-assuan.c
 	$(CC) $(CFLAGS) $(CPPFLAGS) $(ASSUAN_CPPFLAGS) $(LDFLAGS) -o $@ $< $(LIBS) $(ASSUAN_LIBS)
 
+check-assuan2: check-assuan2.c
+	$(CC) $(CFLAGS) $(CPPFLAGS) $(ASSUAN_CPPFLAGS) $(LDFLAGS) -o $@ $< $(LIBS) $(ASSUAN_LIBS)
+
 confclean:
 	rm -f $(CONFIGTESTS) $(CONFIGIN) $(CONFIGCLEANADD)
 
 	conf_check check-sysexits.o NO_SYSEXITS '<sysexits.h>'
 	conf_check check-mmapio.o NO_MMAPIO 'mmap() & ftruncate()'
 	conf_check check-termios.o NO_TERMIOS 'termios'
-	conf_check "${ASSUAN_CHECK}" NO_ASSUAN 'assuan'
+	conf_check "${ASSUAN2_CHECK}" NO_ASSUAN2 'assuan-2'
+	if [ -n "${ASSUAN2_CHECK}" -a ! -f "${ASSUAN2_CHECK}" ]; then
+		conf_check "${ASSUAN_CHECK}" NO_ASSUAN 'assuan'
+	fi
 }
 
 conf_help() {
 	ASSUAN_LIBS=$(libassuan-config --libs 2>/dev/null)
 	: ${ASSUAN_LIBS:=-lassuan} # fallback
 
-	ASSUAN_CHECK=check-assuan
+	ASSUAN2_CHECK='check-assuan2'
+	ASSUAN_CHECK='check-assuan'
 fi
 
 echo >&2
 make ${MAKEFLAGS:-${MAKEOPTS}} -f ${MAKEIN} -k \
 	ASSUAN_CPPFLAGS="${ASSUAN_CPPFLAGS}" \
 	ASSUAN_LIBS="${ASSUAN_LIBS}" \
-	ASSUAN_CHECK="${ASSUAN_CHECK}" \
+	ASSUAN_CHECK="${ASSUAN2_CHECK} ${ASSUAN_CHECK}" \
 	configure
 
 echo "<< 'make configure' done" >&2
 echo >&2
 
 if [ -z "${ASSUAN_CHECK}" -o ! -f "${ASSUAN_CHECK}" ]; then
-	ASSUAN_CPPFLAGS=
-	ASSUAN_LIBS=
+	if [ -z "${ASSUAN2_CHECK}" -o ! -f "${ASSUAN2_CHECK}" ]; then
+		ASSUAN_CPPFLAGS=
+		ASSUAN_LIBS=
+	fi
 fi
 
 conf_results > mirage-config.h

mirage-password.c

 
 #ifndef NO_ASSUAN
 #	include <stddef.h>
+#	ifndef NO_ASSUAN2
+#		include <gpg-error.h>
+#	endif
 #	include <assuan.h>
 #endif
 
 	return "/bin/sh";
 }
 
+#ifndef NO_ASSUAN2
+/* this should be less risky than redefining gpg_* for assuan1 */
+
+typedef gpg_error_t assuan_error_t;
+const assuan_error_t ASSUAN_No_Error = GPG_ERR_NO_ERROR;
+
+inline const char* assuan_strerror(assuan_error_t err) {
+	return gpg_strerror(err);
+}
+
+#else
+
+inline assuan_error_t assuan_release(const assuan_context_t ctx) {
+	assuan_disconnect(ctx);
+	return 0;
+}
+
+#endif
+
 static mirage_tristate_t mirage_pinentry_set(assuan_context_t ctx, const char* const cmd) {
 	assuan_error_t err;
 	char *rcvbuf;
 
 static mirage_tristate_t mirage_input_password_pinentry(void) {
 	const char* const shell = mirage_getshell();
-	const char* const args[] = { shell, "-c", "exec pinentry", NULL };
+	const char* args[] = { shell, "-c", "exec pinentry", NULL };
 	int noclose[] = { -1 };
 
 	assuan_context_t ctx;
 	assuan_error_t err;
 
+#ifndef NO_ASSUAN2
+	if (((err = assuan_new(&ctx))) != GPG_ERR_NO_ERROR) {
+		fprintf(stderr, "Failed to initialize libassuan: %s\n", assuan_strerror(err));
+		return error;
+	}
+
+	if (((err = assuan_pipe_connect(ctx, shell, args, noclose, NULL, NULL, 0))) != GPG_ERR_NO_ERROR) {
+#else
 	if (((err = assuan_pipe_connect(&ctx, shell, args, noclose))) != ASSUAN_No_Error) {
+#endif
 		fprintf(stderr, "Failed to launch pinentry: %s\n", assuan_strerror(err));
 		return error;
 	}
 			|| !mirage_pinentry_set(ctx, "SETPROMPT Pass:")
 			|| !mirage_pinentry_set(ctx, "SETTITLE mirage2iso")) {
 
-		assuan_disconnect(ctx);
+		assuan_release(ctx);
 		return error;
 	}
 
 
 	if (((err = assuan_write_line(ctx, "GETPIN"))) != ASSUAN_No_Error) {
 		fprintf(stderr, "Failed to send the password request to pinentry: %s\n", assuan_strerror(err));
-		assuan_disconnect(ctx);
+		assuan_release(ctx);
 		return error;
 	}
 
 	/* we get either 'D <password>' here or 'ERR nnnnn desc' */
 	if (((err = assuan_read_line(ctx, &rcvbuf, &rcvlen))) != ASSUAN_No_Error) {
 		fprintf(stderr, "Failed to receive the password response from pinentry: %s\n", assuan_strerror(err));
-		assuan_disconnect(ctx);
+		assuan_release(ctx);
 		return error;
 	}
 
 	if (rcvlen <= 2 || strncmp(rcvbuf, "D ", 2)) {
 		fprintf(stderr, "No password supplied\n");
-		assuan_disconnect(ctx);
+		assuan_release(ctx);
 		return failure;
 	}
 
 	if (!mirage_allocbuf(rcvlen - 1)) {
-		assuan_disconnect(ctx);
+		assuan_release(ctx);
 		return error;
 	}
 	strncpy(buf, &rcvbuf[2], rcvlen - 2);
 	if (((err = assuan_read_line(ctx, &rcvbuf, &rcvlen))) != ASSUAN_No_Error) {
 		fprintf(stderr, "Failed to receive a confirmation from pinentry: %s\n", assuan_strerror(err));
 		mirage_forget_password();
-		assuan_disconnect(ctx);
+		assuan_release(ctx);
 		return error;
 	}
 
 	if (rcvlen != 2 || strncmp(rcvbuf, "OK", 2)) {
 		fprintf(stderr, "pinentry didn't confirm sent password\n");
 		mirage_forget_password();
-		assuan_disconnect(ctx);
+		assuan_release(ctx);
 		return error;
 	}
 
 	assuan_end_confidential(ctx);
-	assuan_disconnect(ctx);
+	assuan_release(ctx);
 
 	return success;
 }