Page MenuHomeFreeBSD

D48241.id148512.diff
No OneTemporary

D48241.id148512.diff

diff --git a/usr.sbin/bhyve/Makefile b/usr.sbin/bhyve/Makefile
--- a/usr.sbin/bhyve/Makefile
+++ b/usr.sbin/bhyve/Makefile
@@ -56,6 +56,7 @@
pci_xhci.c \
qemu_fwcfg.c \
qemu_loader.c \
+ rendezvous.c \
smbiostbl.c \
sockstream.c \
tpm_device.c \
diff --git a/usr.sbin/bhyve/bhyverun.c b/usr.sbin/bhyve/bhyverun.c
--- a/usr.sbin/bhyve/bhyverun.c
+++ b/usr.sbin/bhyve/bhyverun.c
@@ -81,6 +81,7 @@
#include "mem.h"
#include "mevent.h"
#include "pci_emul.h"
+#include "rendezvous.h"
#ifdef __amd64__
#include "amd64/pci_lpc.h"
#endif
@@ -764,7 +765,7 @@
#ifdef BHYVE_GDB
init_gdb(ctx);
#endif
-
+ rendezvous();
/*
* Add all vCPUs.
*/
diff --git a/usr.sbin/bhyve/debug.h b/usr.sbin/bhyve/debug.h
--- a/usr.sbin/bhyve/debug.h
+++ b/usr.sbin/bhyve/debug.h
@@ -28,6 +28,7 @@
#ifndef _DEBUG_H_
#define _DEBUG_H_
+#include <stdio.h>
extern int raw_stdio;
diff --git a/usr.sbin/bhyve/debug.h b/usr.sbin/bhyve/rendezvous.h
copy from usr.sbin/bhyve/debug.h
copy to usr.sbin/bhyve/rendezvous.h
--- a/usr.sbin/bhyve/debug.h
+++ b/usr.sbin/bhyve/rendezvous.h
@@ -1,7 +1,7 @@
/*-
* SPDX-License-Identifier: BSD-2-Clause
*
- * Copyright (c) 2019 Vincenzo Maffione <vmaffione@freebsd.org>
+ * Copyright (c) 2024 SHENGYI HONG <aokblast@FreeBSD.org>
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
@@ -25,21 +25,25 @@
* SUCH DAMAGE.
*/
-#ifndef _DEBUG_H_
-#define _DEBUG_H_
+#ifndef _RENDEZVOUS_H_
+#define _RENDEZVOUS_H_
+#include <pthread.h>
+#include <stdbool.h>
-extern int raw_stdio;
+struct rendezvous_member;
-#define FPRINTLN(filep, fmt, arg...) \
- do { \
- if (raw_stdio) \
- fprintf(filep, fmt "\r\n", ##arg); \
- else \
- fprintf(filep, fmt "\n", ##arg); \
- } while (0)
+typedef struct rendezvous_member *rendezvous_member_t;
-#define PRINTLN(fmt, arg...) FPRINTLN(stdout, fmt, ##arg)
-#define EPRINTLN(fmt, arg...) FPRINTLN(stderr, fmt, ##arg)
+rendezvous_member_t rendezvous_member_create(const char *name);
-#endif
+/*
+ * notify will send the member to main thread, the main thread will takes
+ * the responsibility to destory the resource of rendezvous. Thus the caller
+ * should consider the member is destroyed after using rendezvous_member_notify.
+ */
+void rendezvous_member_notify(rendezvous_member_t member);
+bool rendezvous_add_member(rendezvous_member_t member);
+void rendezvous(void);
+
+#endif /* _RENDEZVOUS_H_ */
diff --git a/usr.sbin/bhyve/rendezvous.c b/usr.sbin/bhyve/rendezvous.c
new file mode 100644
--- /dev/null
+++ b/usr.sbin/bhyve/rendezvous.c
@@ -0,0 +1,115 @@
+/*-
+ * SPDX-License-Identifier: BSD-2-Clause
+ *
+ * Copyright (c) 2024 SHENGYI HONG <aokblast@FreeBSD.org>
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+
+#include <err.h>
+#include <pthread.h>
+#include <stdlib.h>
+
+#include "debug.h"
+#include "rendezvous.h"
+
+/*
+ * The rendezvous layer provide a abstraction when components in bhyve like rfb
+ * and tcp socket needs to wait for connection, when more than two wait is
+ * specified, the original design will depends on the order of arguments passed
+ * to the bhyve itself. Currently, the gdb part does not join the rendezvous
+ * because GDB stop the vcpu when wait force connection.
+ */
+
+/*
+ * not so much components in the bhyve userspace needs to wait,
+ * set to 10 so that we can modify it to be capable to wait more
+ * components
+ */
+#define MEMBERS_LIMIT 10
+
+typedef struct rendezvous_member {
+ pthread_mutex_t
+ mtx; /* lock prevent race condition from member and wait thread */
+ pthread_cond_t cond; /* cond variable to notify the wait thread */
+ const char *name;
+} rendezvous_member;
+
+static rendezvous_member_t members[MEMBERS_LIMIT];
+static int total_members = 0;
+
+rendezvous_member_t
+rendezvous_member_create(const char *name)
+{
+ int error;
+ rendezvous_member_t member = malloc(sizeof(rendezvous_member));
+
+ if ((error = pthread_mutex_init(&member->mtx, NULL)) != 0) {
+ errc(1, error, "rendezvous mutex %s init", name);
+ goto error;
+ }
+
+ if ((error = pthread_cond_init(&member->cond, NULL)) != 0) {
+ errc(1, error, "rendezvous cond %s init", name);
+ goto error;
+ }
+
+ member->name = name;
+ return (member);
+error:
+ free(member);
+ return (NULL);
+}
+
+void
+rendezvous_member_notify(rendezvous_member_t member)
+{
+ pthread_mutex_lock(&member->mtx);
+ pthread_cond_signal(&member->cond);
+ pthread_mutex_unlock(&member->mtx);
+}
+
+bool
+rendezvous_add_member(rendezvous_member_t member)
+{
+ if (total_members + 1 > MEMBERS_LIMIT)
+ return (false);
+
+ members[total_members++] = member;
+ return (true);
+}
+
+void
+rendezvous(void)
+{
+ int i = 0;
+
+ for (i = 0; i < total_members; i++) {
+ pthread_mutex_lock(&members[i]->mtx);
+ pthread_cond_wait(&members[i]->cond, &members[i]->mtx);
+ pthread_mutex_unlock(&members[i]->mtx);
+ pthread_cond_destroy(&members[i]->cond);
+ pthread_mutex_destroy(&members[i]->mtx);
+ PRINTLN("%s in here!", members[i]->name);
+ free(members[i]);
+ }
+}
diff --git a/usr.sbin/bhyve/rfb.c b/usr.sbin/bhyve/rfb.c
--- a/usr.sbin/bhyve/rfb.c
+++ b/usr.sbin/bhyve/rfb.c
@@ -52,17 +52,17 @@
#include <pthread_np.h>
#include <signal.h>
#include <stdbool.h>
-#include <stdlib.h>
#include <stdio.h>
+#include <stdlib.h>
#include <string.h>
#include <sysexits.h>
#include <unistd.h>
-
#include <zlib.h>
#include "bhyvegc.h"
-#include "debug.h"
#include "console.h"
+#include "debug.h"
+#include "rendezvous.h"
#include "rfb.h"
#include "sockstream.h"
@@ -140,9 +140,8 @@
atomic_bool input_detected;
atomic_bool update_pixfmt;
- pthread_mutex_t mtx;
pthread_mutex_t pixfmt_mtx;
- pthread_cond_t cond;
+ rendezvous_member_t rendezvous;
int hw_crc;
uint32_t *crc; /* WxH crc cells */
@@ -1225,9 +1224,8 @@
cfd = accept(rc->sfd, NULL, NULL);
if (rc->conn_wait) {
- pthread_mutex_lock(&rc->mtx);
- pthread_cond_signal(&rc->cond);
- pthread_mutex_unlock(&rc->mtx);
+ rendezvous_member_notify(rc->rendezvous);
+ rc->rendezvous = NULL;
rc->conn_wait = 0;
}
rfb_handle(rc, cfd);
@@ -1329,21 +1327,16 @@
rc->conn_wait = wait;
if (wait) {
- pthread_mutex_init(&rc->mtx, NULL);
- pthread_cond_init(&rc->cond, NULL);
+ rc->rendezvous = rendezvous_member_create("rfb");
+ rendezvous_add_member(rc->rendezvous);
}
pthread_mutex_init(&rc->pixfmt_mtx, NULL);
pthread_create(&rc->tid, NULL, rfb_thr, rc);
pthread_set_name_np(rc->tid, "rfb");
- if (wait) {
+ if (wait)
DPRINTF(("Waiting for rfb client..."));
- pthread_mutex_lock(&rc->mtx);
- pthread_cond_wait(&rc->cond, &rc->mtx);
- pthread_mutex_unlock(&rc->mtx);
- DPRINTF(("rfb client connected"));
- }
freeaddrinfo(ai);
return (0);

File Metadata

Mime Type
text/plain
Expires
Sat, Feb 22, 6:04 PM (9 h, 8 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
16776337
Default Alt Text
D48241.id148512.diff (7 KB)

Event Timeline