Blame SOURCES/redhat-bugzilla-2135314-pmfind-fix.patch

c10532
diff -Naurp pcp-5.3.7.orig/qa/1985 pcp-5.3.7/qa/1985
c10532
--- pcp-5.3.7.orig/qa/1985	1970-01-01 10:00:00.000000000 +1000
c10532
+++ pcp-5.3.7/qa/1985	2022-10-19 21:32:03.971832371 +1100
c10532
@@ -0,0 +1,38 @@
c10532
+#!/bin/sh
c10532
+# PCP QA Test No. 1985
c10532
+# Exercise a pmfind fix - valgrind-enabled variant.
c10532
+#
c10532
+# Copyright (c) 2022 Red Hat.  All Rights Reserved.
c10532
+#
c10532
+
c10532
+seq=`basename $0`
c10532
+echo "QA output created by $seq"
c10532
+
c10532
+# get standard environment, filters and checks
c10532
+. ./common.product
c10532
+. ./common.filter
c10532
+. ./common.check
c10532
+
c10532
+_check_valgrind
c10532
+
c10532
+_cleanup()
c10532
+{
c10532
+    cd $here
c10532
+    $sudo rm -rf $tmp $tmp.*
c10532
+}
c10532
+
c10532
+status=0	# success is the default!
c10532
+$sudo rm -rf $tmp $tmp.* $seq.full
c10532
+trap "_cleanup; exit \$status" 0 1 2 3 15
c10532
+
c10532
+# real QA test starts here
c10532
+export seq
c10532
+./1986 --valgrind \
c10532
+| $PCP_AWK_PROG '
c10532
+skip == 1 && $1 == "==="       { skip = 0 }
c10532
+/^=== std err ===/             { skip = 1 }
c10532
+skip == 0              { print }
c10532
+skip == 1              { print >>"'$here/$seq.full'" }'
c10532
+
c10532
+# success, all done
c10532
+exit
c10532
diff -Naurp pcp-5.3.7.orig/qa/1985.out pcp-5.3.7/qa/1985.out
c10532
--- pcp-5.3.7.orig/qa/1985.out	1970-01-01 10:00:00.000000000 +1000
c10532
+++ pcp-5.3.7/qa/1985.out	2022-10-19 21:32:03.971832371 +1100
c10532
@@ -0,0 +1,11 @@
c10532
+QA output created by 1985
c10532
+QA output created by 1986 --valgrind
c10532
+=== std out ===
c10532
+SOURCE HOSTNAME
c10532
+=== filtered valgrind report ===
c10532
+Memcheck, a memory error detector
c10532
+Command: pmfind -S -m probe=127.0.0.1/32
c10532
+LEAK SUMMARY:
c10532
+definitely lost: 0 bytes in 0 blocks
c10532
+indirectly lost: 0 bytes in 0 blocks
c10532
+ERROR SUMMARY: 0 errors from 0 contexts ...
c10532
diff -Naurp pcp-5.3.7.orig/qa/1986 pcp-5.3.7/qa/1986
c10532
--- pcp-5.3.7.orig/qa/1986	1970-01-01 10:00:00.000000000 +1000
c10532
+++ pcp-5.3.7/qa/1986	2022-10-19 21:32:03.971832371 +1100
c10532
@@ -0,0 +1,62 @@
c10532
+#!/bin/sh
c10532
+# PCP QA Test No. 1986
c10532
+# Exercise libpcp_web timers pmfind regression fix.
c10532
+#
c10532
+# Copyright (c) 2022 Red Hat.  All Rights Reserved.
c10532
+#
c10532
+
c10532
+if [ $# -eq 0 ]
c10532
+then
c10532
+    seq=`basename $0`
c10532
+    echo "QA output created by $seq"
c10532
+else
c10532
+    # use $seq from caller, unless not set
c10532
+    [ -n "$seq" ] || seq=`basename $0`
c10532
+    echo "QA output created by `basename $0` $*"
c10532
+fi
c10532
+
c10532
+# get standard environment, filters and checks
c10532
+. ./common.product
c10532
+. ./common.filter
c10532
+. ./common.check
c10532
+
c10532
+do_valgrind=false
c10532
+if [ "$1" = "--valgrind" ]
c10532
+then
c10532
+    _check_valgrind
c10532
+    do_valgrind=true
c10532
+fi
c10532
+
c10532
+test -x $PCP_BIN_DIR/pmfind || _notrun No support for pmfind
c10532
+
c10532
+_cleanup()
c10532
+{
c10532
+    cd $here
c10532
+    $sudo rm -rf $tmp $tmp.*
c10532
+}
c10532
+
c10532
+status=0	# success is the default!
c10532
+hostname=`hostname || echo localhost`
c10532
+$sudo rm -rf $tmp $tmp.* $seq.full
c10532
+trap "_cleanup; exit \$status" 0 1 2 3 15
c10532
+
c10532
+_filter()
c10532
+{
c10532
+    sed \
c10532
+	-e "s@$tmp@TMP@g" \
c10532
+	-e "s/ $hostname/ HOSTNAME/" \
c10532
+	-e 's/^[a-f0-9][a-f0-9]* /SOURCE /' \
c10532
+    # end
c10532
+}
c10532
+
c10532
+# real QA test starts here
c10532
+if $do_valgrind
c10532
+then
c10532
+    _run_valgrind pmfind -S -m probe=127.0.0.1/32
c10532
+else
c10532
+    pmfind -S -m probe=127.0.0.1/32
c10532
+fi \
c10532
+| _filter
c10532
+
c10532
+# success, all done
c10532
+exit
c10532
diff -Naurp pcp-5.3.7.orig/qa/1986.out pcp-5.3.7/qa/1986.out
c10532
--- pcp-5.3.7.orig/qa/1986.out	1970-01-01 10:00:00.000000000 +1000
c10532
+++ pcp-5.3.7/qa/1986.out	2022-10-19 21:32:03.971832371 +1100
c10532
@@ -0,0 +1,2 @@
c10532
+QA output created by 1986
c10532
+SOURCE HOSTNAME
c10532
diff -Naurp pcp-5.3.7.orig/qa/group pcp-5.3.7/qa/group
c10532
--- pcp-5.3.7.orig/qa/group	2022-10-19 20:49:42.638708707 +1100
c10532
+++ pcp-5.3.7/qa/group	2022-10-19 21:32:03.972832359 +1100
c10532
@@ -1974,4 +1974,6 @@ x11
c10532
 1957 libpcp local valgrind
c10532
 1978 atop local
c10532
 1984 pmlogconf pmda.redis local
c10532
+1985 pmfind local valgrind
c10532
+1986 pmfind local
c10532
 4751 libpcp threads valgrind local pcp helgrind
c10532
diff -Naurp pcp-5.3.7.orig/src/libpcp_web/src/webgroup.c pcp-5.3.7/src/libpcp_web/src/webgroup.c
c10532
--- pcp-5.3.7.orig/src/libpcp_web/src/webgroup.c	2021-11-01 13:02:26.000000000 +1100
c10532
+++ pcp-5.3.7/src/libpcp_web/src/webgroup.c	2022-10-19 21:32:03.973832346 +1100
c10532
@@ -287,11 +287,24 @@ webgroup_new_context(pmWebGroupSettings
c10532
 }
c10532
 
c10532
 static void
c10532
+webgroup_timers_stop(struct webgroups *groups)
c10532
+{
c10532
+    if (groups->active) {
c10532
+	uv_timer_stop(&groups->timer);
c10532
+	uv_close((uv_handle_t *)&groups->timer, NULL);
c10532
+	pmWebTimerRelease(groups->timerid);
c10532
+	groups->timerid = -1;
c10532
+	groups->active = 0;
c10532
+    }
c10532
+}
c10532
+
c10532
+static void
c10532
 webgroup_garbage_collect(struct webgroups *groups)
c10532
 {
c10532
     dictIterator        *iterator;
c10532
     dictEntry           *entry;
c10532
     context_t		*cp;
c10532
+    unsigned int	count = 0, drops = 0;
c10532
 
c10532
     if (pmDebugOptions.http || pmDebugOptions.libweb)
c10532
 	fprintf(stderr, "%s: started\n", "webgroup_garbage_collect");
c10532
@@ -308,33 +321,40 @@ webgroup_garbage_collect(struct webgroup
c10532
 		uv_mutex_unlock(&groups->mutex);
c10532
 		webgroup_drop_context(cp, groups);
c10532
 		uv_mutex_lock(&groups->mutex);
c10532
+		drops++;
c10532
 	    }
c10532
+	    count++;
c10532
 	}
c10532
 	dictReleaseIterator(iterator);
c10532
+
c10532
+	/* if dropping the last remaining context, do cleanup */
c10532
+	if (groups->active && drops == count) {
c10532
+	    if (pmDebugOptions.http || pmDebugOptions.libweb)
c10532
+		fprintf(stderr, "%s: freezing\n", "webgroup_garbage_collect");
c10532
+	    webgroup_timers_stop(groups);
c10532
+	}
c10532
 	uv_mutex_unlock(&groups->mutex);
c10532
     }
c10532
 
c10532
     if (pmDebugOptions.http || pmDebugOptions.libweb)
c10532
-	fprintf(stderr, "%s: finished\n", "webgroup_garbage_collect");
c10532
+	fprintf(stderr, "%s: finished [%u drops from %u entries]\n",
c10532
+			"webgroup_garbage_collect", drops, count);
c10532
 }
c10532
 
c10532
 static void
c10532
 refresh_maps_metrics(void *data)
c10532
 {
c10532
     struct webgroups	*groups = (struct webgroups *)data;
c10532
+    unsigned int	value;
c10532
 
c10532
-    if (groups->metrics) {
c10532
-	unsigned int	value;
c10532
-
c10532
-	value = dictSize(contextmap);
c10532
-	mmv_set(groups->map, groups->metrics[CONTEXT_MAP_SIZE], &value);
c10532
-	value = dictSize(namesmap);
c10532
-	mmv_set(groups->map, groups->metrics[NAMES_MAP_SIZE], &value);
c10532
-	value = dictSize(labelsmap);
c10532
-	mmv_set(groups->map, groups->metrics[LABELS_MAP_SIZE], &value);
c10532
-	value = dictSize(instmap);
c10532
-	mmv_set(groups->map, groups->metrics[INST_MAP_SIZE], &value);
c10532
-    }
c10532
+    value = contextmap? dictSize(contextmap) : 0;
c10532
+    mmv_set(groups->map, groups->metrics[CONTEXT_MAP_SIZE], &value);
c10532
+    value = namesmap? dictSize(namesmap) : 0;
c10532
+    mmv_set(groups->map, groups->metrics[NAMES_MAP_SIZE], &value);
c10532
+    value = labelsmap? dictSize(labelsmap) : 0;
c10532
+    mmv_set(groups->map, groups->metrics[LABELS_MAP_SIZE], &value);
c10532
+    value = instmap? dictSize(instmap) : 0;
c10532
+    mmv_set(groups->map, groups->metrics[INST_MAP_SIZE], &value);
c10532
 }
c10532
 
c10532
 static void
c10532
@@ -487,6 +507,7 @@ pmWebGroupDestroy(pmWebGroupSettings *se
c10532
 	if (pmDebugOptions.libweb)
c10532
 	    fprintf(stderr, "%s: destroy context %p gp=%p\n", "pmWebGroupDestroy", cp, gp);
c10532
 
c10532
+	webgroup_deref_context(cp);
c10532
 	webgroup_drop_context(cp, gp);
c10532
     }
c10532
     sdsfree(msg);
c10532
@@ -2394,17 +2415,12 @@ pmWebGroupClose(pmWebGroupModule *module
c10532
 
c10532
     if (groups) {
c10532
 	/* walk the contexts, stop timers and free resources */
c10532
-	if (groups->active) {
c10532
-	    groups->active = 0;
c10532
-	    uv_timer_stop(&groups->timer);
c10532
-	    pmWebTimerRelease(groups->timerid);
c10532
-	    groups->timerid = -1;
c10532
-	}
c10532
 	iterator = dictGetIterator(groups->contexts);
c10532
 	while ((entry = dictNext(iterator)) != NULL)
c10532
 	    webgroup_drop_context((context_t *)dictGetVal(entry), NULL);
c10532
 	dictReleaseIterator(iterator);
c10532
 	dictRelease(groups->contexts);
c10532
+	webgroup_timers_stop(groups);
c10532
 	memset(groups, 0, sizeof(struct webgroups));
c10532
 	free(groups);
c10532
     }
c10532
diff -Naurp pcp-5.3.7.orig/src/pmfind/source.c pcp-5.3.7/src/pmfind/source.c
c10532
--- pcp-5.3.7.orig/src/pmfind/source.c	2021-02-17 15:27:41.000000000 +1100
c10532
+++ pcp-5.3.7/src/pmfind/source.c	2022-10-19 21:32:03.973832346 +1100
c10532
@@ -1,5 +1,5 @@
c10532
 /*
c10532
- * Copyright (c) 2020 Red Hat.
c10532
+ * Copyright (c) 2020,2022 Red Hat.
c10532
  *
c10532
  * This program is free software; you can redistribute it and/or modify it
c10532
  * under the terms of the GNU General Public License as published by the
c10532
@@ -25,6 +25,7 @@ static pmWebGroupSettings settings;
c10532
 typedef struct {
c10532
     sds			source;
c10532
     sds			hostspec;
c10532
+    unsigned int	refcount;
c10532
 } context_t;
c10532
 
c10532
 typedef struct {
c10532
@@ -38,22 +39,34 @@ typedef struct {
c10532
 } sources_t;
c10532
 
c10532
 static void
c10532
+source_release(sources_t *sp, context_t *cp, sds ctx)
c10532
+{
c10532
+    pmWebGroupDestroy(&settings, ctx, sp);
c10532
+    sdsfree(cp->hostspec);
c10532
+    sdsfree(cp->source);
c10532
+    free(cp);
c10532
+}
c10532
+
c10532
+static void
c10532
 sources_release(void *arg, const struct dictEntry *entry)
c10532
 {
c10532
     sources_t	*sp = (sources_t *)arg;
c10532
     context_t	*cp = (context_t *)dictGetVal(entry);
c10532
     sds		ctx = (sds)entry->key;
c10532
 
c10532
-    pmWebGroupDestroy(&settings, ctx, sp);
c10532
-    sdsfree(cp->hostspec);
c10532
-    sdsfree(cp->source);
c10532
+    if (pmDebugOptions.discovery)
c10532
+	fprintf(stderr, "releasing context %s\n", ctx);
c10532
+
c10532
+    source_release(sp, cp, ctx);
c10532
 }
c10532
 
c10532
 static void
c10532
-sources_containers(sources_t *sp, sds id, dictEntry *uniq)
c10532
+sources_containers(sources_t *sp, context_t *cp, sds id, dictEntry *uniq)
c10532
 {
c10532
     uv_mutex_lock(&sp->mutex);
c10532
-    sp->count++;	/* issuing another PMWEBAPI request */
c10532
+    /* issuing another PMWEBAPI request */
c10532
+    sp->count++;
c10532
+    cp->refcount++;
c10532
     uv_mutex_unlock(&sp->mutex);
c10532
 
c10532
     pmWebGroupScrape(&settings, id, sp->params, sp);
c10532
@@ -75,6 +88,7 @@ on_source_context(sds id, pmWebSource *s
c10532
 
c10532
     cp->source = sdsdup(src->source);
c10532
     cp->hostspec = sdsdup(src->hostspec);
c10532
+    cp->refcount = 1;
c10532
 
c10532
     uv_mutex_lock(&sp->mutex);
c10532
     dictAdd(sp->contexts, id, cp);
c10532
@@ -84,7 +98,7 @@ on_source_context(sds id, pmWebSource *s
c10532
     if (entry) {	/* source just discovered */
c10532
 	printf("%s %s\n", src->source, src->hostspec);
c10532
 	if (containers)
c10532
-	    sources_containers(sp, id, entry);
c10532
+	    sources_containers(sp, cp, id, entry);
c10532
     }
c10532
 }
c10532
 
c10532
@@ -116,7 +130,9 @@ static void
c10532
 on_source_done(sds context, int status, sds message, void *arg)
c10532
 {
c10532
     sources_t	*sp = (sources_t *)arg;
c10532
-    int		count = 0, release = 0;
c10532
+    context_t	*cp;
c10532
+    dictEntry	*he;
c10532
+    int		remove = 0, count = 0, release = 0;
c10532
 
c10532
     if (pmDebugOptions.discovery)
c10532
 	fprintf(stderr, "done on context %s (sts=%d)\n", context, status);
c10532
@@ -127,19 +143,26 @@ on_source_done(sds context, int status,
c10532
     uv_mutex_lock(&sp->mutex);
c10532
     if ((count = --sp->count) <= 0)
c10532
 	release = 1;
c10532
+    if ((he = dictFind(sp->contexts, context)) != NULL &&
c10532
+	(cp = (context_t *)dictGetVal(he)) != NULL &&
c10532
+	(--cp->refcount <= 0))
c10532
+	remove = 1;
c10532
     uv_mutex_unlock(&sp->mutex);
c10532
 
c10532
+    if (remove) {
c10532
+	if (pmDebugOptions.discovery)
c10532
+	    fprintf(stderr, "remove context %s\n", context);
c10532
+	source_release(sp, cp, context);
c10532
+	dictDelete(sp->contexts, context);
c10532
+    }
c10532
+
c10532
     if (release) {
c10532
 	unsigned long	cursor = 0;
c10532
-
c10532
-	if (pmDebugOptions.discovery)
c10532
-	   fprintf(stderr, "release context %s (sts=%d)\n", context, status);
c10532
 	do {
c10532
 	    cursor = dictScan(sp->contexts, cursor, sources_release, NULL, sp);
c10532
 	} while (cursor);
c10532
-    } else {
c10532
-	if (pmDebugOptions.discovery)
c10532
-	    fprintf(stderr, "not yet releasing (count=%d)\n", count);
c10532
+    } else if (pmDebugOptions.discovery) {
c10532
+	fprintf(stderr, "not yet releasing (count=%d)\n", count);
c10532
     }
c10532
 }
c10532
 
c10532
@@ -190,6 +213,7 @@ sources_discovery_start(uv_timer_t *arg)
c10532
     }
c10532
 
c10532
     dictRelease(dp);
c10532
+    pmWebTimerClose();
c10532
 }
c10532
 
c10532
 /*
c10532
@@ -214,8 +238,8 @@ source_discovery(int count, char **urls)
c10532
     uv_mutex_init(&find.mutex);
c10532
     find.urls = urls;
c10532
     find.count = count;	/* at least one PMWEBAPI request for each url */
c10532
-    find.uniq = dictCreate(&sdsDictCallBacks, NULL);
c10532
-    find.params = dictCreate(&sdsDictCallBacks, NULL);
c10532
+    find.uniq = dictCreate(&sdsKeyDictCallBacks, NULL);
c10532
+    find.params = dictCreate(&sdsOwnDictCallBacks, NULL);
c10532
     dictAdd(find.params, sdsnew("name"), sdsnew("containers.state.running"));
c10532
     find.contexts = dictCreate(&sdsKeyDictCallBacks, NULL);
c10532
 
c10532
@@ -230,6 +254,7 @@ source_discovery(int count, char **urls)
c10532
 
c10532
     pmWebGroupSetup(&settings.module);
c10532
     pmWebGroupSetEventLoop(&settings.module, loop);
c10532
+    pmWebTimerSetEventLoop(loop);
c10532
 
c10532
     /*
c10532
      * Start a one-shot timer to add a start function into the loop
c10532
@@ -244,7 +269,9 @@ source_discovery(int count, char **urls)
c10532
     /*
c10532
      * Finished, release all resources acquired so far
c10532
      */
c10532
+    pmWebGroupClose(&settings.module);
c10532
     uv_mutex_destroy(&find.mutex);
c10532
+    dictRelease(find.uniq);
c10532
     dictRelease(find.params);
c10532
     dictRelease(find.contexts);
c10532
     return find.status;
c10532
diff -Naurp pcp-5.3.7.orig/src/pmproxy/src/server.c pcp-5.3.7/src/pmproxy/src/server.c
c10532
--- pcp-5.3.7.orig/src/pmproxy/src/server.c	2022-04-05 09:05:43.000000000 +1000
c10532
+++ pcp-5.3.7/src/pmproxy/src/server.c	2022-10-19 21:31:43.831093354 +1100
c10532
@@ -1,5 +1,5 @@
c10532
 /*
c10532
- * Copyright (c) 2018-2019,2021 Red Hat.
c10532
+ * Copyright (c) 2018-2019,2021-2022 Red Hat.
c10532
  *
c10532
  * This program is free software; you can redistribute it and/or modify it
c10532
  * under the terms of the GNU Lesser General Public License as published
c10532
@@ -310,17 +310,21 @@ on_write_callback(uv_callback_t *handle,
c10532
     struct client		*client = (struct client *)request->writer.data;
c10532
     int				sts;
c10532
 
c10532
+    (void)handle;
c10532
     if (pmDebugOptions.af)
c10532
 	fprintf(stderr, "%s: client=%p\n", "on_write_callback", client);
c10532
 
c10532
     if (client->stream.secure == 0) {
c10532
 	sts = uv_write(&request->writer, (uv_stream_t *)&client->stream,
c10532
 		 &request->buffer[0], request->nbuffers, request->callback);
c10532
-	if (sts != 0)
c10532
-	    fprintf(stderr, "%s: ERROR uv_write failed\n", "on_write_callback");
c10532
+	if (sts != 0) {
c10532
+	    pmNotifyErr(LOG_ERR, "%s: %s - uv_write failed [%s]: %s\n",
c10532
+			pmGetProgname(), "on_write_callback",
c10532
+			uv_err_name(sts), uv_strerror(sts));
c10532
+	    client_close(client);
c10532
+	}
c10532
     } else
c10532
 	secure_client_write(client, request);
c10532
-    (void)handle;
c10532
     return 0;
c10532
 }
c10532
 
c10532
@@ -455,14 +459,16 @@ on_client_connection(uv_stream_t *stream
c10532
     uv_handle_t		*handle;
c10532
 
c10532
     if (status != 0) {
c10532
-	fprintf(stderr, "%s: client connection failed: %s\n",
c10532
-			pmGetProgname(), uv_strerror(status));
c10532
+	pmNotifyErr(LOG_ERR, "%s: %s - %s failed [%s]: %s\n",
c10532
+		    pmGetProgname(), "on_client_connection", "connection",
c10532
+		    uv_err_name(status), uv_strerror(status));
c10532
 	return;
c10532
     }
c10532
 
c10532
     if ((client = calloc(1, sizeof(*client))) == NULL) {
c10532
-	fprintf(stderr, "%s: out-of-memory for new client\n",
c10532
-			pmGetProgname());
c10532
+	pmNotifyErr(LOG_ERR, "%s: %s - %s failed [%s]: %s\n",
c10532
+			pmGetProgname(), "on_client_connection", "calloc",
c10532
+			"ENOMEM", strerror(ENOMEM));
c10532
 	return;
c10532
     }
c10532
     if (pmDebugOptions.context | pmDebugOptions.af)
c10532
@@ -476,16 +482,18 @@ on_client_connection(uv_stream_t *stream
c10532
 
c10532
     status = uv_tcp_init(proxy->events, &client->stream.u.tcp);
c10532
     if (status != 0) {
c10532
-	fprintf(stderr, "%s: client tcp init failed: %s\n",
c10532
-			pmGetProgname(), uv_strerror(status));
c10532
+	pmNotifyErr(LOG_ERR, "%s: %s - %s failed [%s]: %s\n",
c10532
+		    pmGetProgname(), "on_client_connection", "uv_tcp_init",
c10532
+		    uv_err_name(status), uv_strerror(status));
c10532
 	client_put(client);
c10532
 	return;
c10532
     }
c10532
 
c10532
     status = uv_accept(stream, (uv_stream_t *)&client->stream.u.tcp);
c10532
     if (status != 0) {
c10532
-	fprintf(stderr, "%s: client tcp init failed: %s\n",
c10532
-			pmGetProgname(), uv_strerror(status));
c10532
+	pmNotifyErr(LOG_ERR, "%s: %s - %s failed [%s]: %s\n",
c10532
+		    pmGetProgname(), "on_client_connection", "uv_accept",
c10532
+		    uv_err_name(status), uv_strerror(status));
c10532
 	client_put(client);
c10532
 	return;
c10532
     }
c10532
@@ -496,8 +504,9 @@ on_client_connection(uv_stream_t *stream
c10532
     status = uv_read_start((uv_stream_t *)&client->stream.u.tcp,
c10532
 			    on_buffer_alloc, on_client_read);
c10532
     if (status != 0) {
c10532
-	fprintf(stderr, "%s: client read start failed: %s\n",
c10532
-			pmGetProgname(), uv_strerror(status));
c10532
+	pmNotifyErr(LOG_ERR, "%s: %s - %s failed [%s]: %s\n",
c10532
+		    pmGetProgname(), "on_client_connection", "uv_read_start",
c10532
+		    uv_err_name(status), uv_strerror(status));
c10532
 	client_close(client);
c10532
     }
c10532
 }
c10532
@@ -530,8 +539,9 @@ open_request_port(struct proxy *proxy, s
c10532
 
c10532
     sts = uv_listen((uv_stream_t *)&stream->u.tcp, maxpending, on_client_connection);
c10532
     if (sts != 0) {
c10532
-	fprintf(stderr, "%s: socket listen error %s\n",
c10532
-			pmGetProgname(), uv_strerror(sts));
c10532
+	pmNotifyErr(LOG_ERR, "%s: %s - uv_listen failed [%s]: %s\n",
c10532
+			pmGetProgname(), "open_request_port",
c10532
+			uv_err_name(sts), uv_strerror(sts));
c10532
 	uv_close(handle, NULL);
c10532
 	return -ENOTCONN;
c10532
     }
c10532
@@ -554,15 +564,23 @@ open_request_local(struct proxy *proxy,
c10532
     uv_pipe_init(proxy->events, &stream->u.local, 0);
c10532
     handle = (uv_handle_t *)&stream->u.local;
c10532
     handle->data = (void *)proxy;
c10532
-    uv_pipe_bind(&stream->u.local, name);
c10532
+    sts = uv_pipe_bind(&stream->u.local, name);
c10532
+    if (sts != 0) {
c10532
+	pmNotifyErr(LOG_ERR, "%s: %s - uv_pipe_bind %s failed [%s]: %s\n",
c10532
+			pmGetProgname(), "open_request_local", name,
c10532
+			uv_err_name(sts), uv_strerror(sts));
c10532
+	uv_close(handle, NULL);
c10532
+	return -ENOTCONN;
c10532
+    }
c10532
 #ifdef HAVE_UV_PIPE_CHMOD
c10532
     uv_pipe_chmod(&stream->u.local, UV_READABLE | UV_WRITABLE);
c10532
 #endif
c10532
 
c10532
     sts = uv_listen((uv_stream_t *)&stream->u.local, maxpending, on_client_connection);
c10532
     if (sts != 0) {
c10532
-	fprintf(stderr, "%s: local listen error %s\n",
c10532
-			pmGetProgname(), uv_strerror(sts));
c10532
+	pmNotifyErr(LOG_ERR, "%s: %s - %s failed [%s]: %s\n",
c10532
+		    pmGetProgname(), "open_request_local", "uv_listen",
c10532
+		    uv_err_name(sts), uv_strerror(sts));
c10532
 	uv_close(handle, NULL);
c10532
         return -ENOTCONN;
c10532
     }