From aabd68b85c23811dd132af85c9738a0089c484f7 Mon Sep 17 00:00:00 2001 From: Watto <45884543+wattoc@users.noreply.github.com> Date: Sat, 4 Dec 2021 06:47:30 +0000 Subject: [PATCH] WIP: Virtualbox Additions (#6152) * Add Virtualbox 6.1.26 Additions recipe --- ...virtualbox_guest_additions-6.1.26.patchset | 3309 +++++++++++++++++ .../virtualbox_guest_additions-6.1.26.recipe | 108 + 2 files changed, 3417 insertions(+) create mode 100644 app-emulation/virtualbox-guest-additions/patches/virtualbox_guest_additions-6.1.26.patchset create mode 100644 app-emulation/virtualbox-guest-additions/virtualbox_guest_additions-6.1.26.recipe diff --git a/app-emulation/virtualbox-guest-additions/patches/virtualbox_guest_additions-6.1.26.patchset b/app-emulation/virtualbox-guest-additions/patches/virtualbox_guest_additions-6.1.26.patchset new file mode 100644 index 000000000..d30b0767e --- /dev/null +++ b/app-emulation/virtualbox-guest-additions/patches/virtualbox_guest_additions-6.1.26.patchset @@ -0,0 +1,3309 @@ +From e690565c6c0244c03f8e947c75b2e1ae50022bfd Mon Sep 17 00:00:00 2001 +From: Craig Watson +Date: Mon, 20 Sep 2021 10:51:35 +0100 +Subject: Fixes for Haiku + + +diff --git a/Config.kmk b/Config.kmk +index ee61f76..07e08ec 100644 +--- a/Config.kmk ++++ b/Config.kmk +@@ -2054,8 +2054,6 @@ ifeq ($(VBOX_XSLTPROC),) + endif + else ifeq ($(KBUILD_HOST),os2) + VBOX_XSLTPROC := BEGINLIBPATH="$(KBUILD_DEVTOOLS_HST)/bin;$$BEGINLIBPATH" $(KBUILD_DEVTOOLS_HST)/bin/xsltproc.exe +- else ifeq ($(KBUILD_HOST),haiku) +- VBOX_XSLTPROC := $(KBUILD_DEVTOOLS)/haiku.x86/bin/xsltproc + else + VBOX_XSLTPROC := xsltproc$(HOSTSUFF_EXE) + endif +@@ -2833,7 +2831,7 @@ endif + $(QUIET)$(APPEND) '$@' ' VBOX_GCC_fvisibility-hidden ?= $(call VBOX_GCC_CHECK_CC,-fvisibility=hidden -DVBOX_HAVE_VISIBILITY_HIDDEN -DRT_USE_VISIBILITY_DEFAULT,)' + $(QUIET)$(APPEND) '$@' ' endif' + $(QUIET)$(APPEND) '$@' 'endif' +-ifn1of ($(KBUILD_TARGET),haiku) ++ifn1of ($(KBUILD_TARGET),jesus) + # Set default attribute for inline functions to ``hidden'' to reduce the number + # of relocation entries and PLT indirections in shared libraries. Don't allow for gcc version < 4. + $(QUIET)$(APPEND) '$@' 'ifneq ($$(VBOX_GCC_VERSION_CXX),)' +@@ -4347,7 +4345,7 @@ ifdef VBOX_WITH_RAW_MODE + + ifeq ($(VBOX_LDR_FMT32),elf) + TEMPLATE_VBoxRc_TOOL = $(VBOX_GCC32_TOOL) +- TEMPLATE_VBoxRc_CXXFLAGS = -fno-pie -nostdinc -g $(VBOX_GCC_pipe) $(VBOX_GCC_WERR) $(VBOX_GCC_PEDANTIC_CXX) $(VBOX_GCC32_Wno-variadic-macros) -fno-exceptions $(VBOX_GCC_GC_OPT) $(VBOX_GCC_GC_FP) -mno-sse -mno-mmx -mno-sse2 -mno-3dnow -fno-strict-aliasing $(VBOX_GCC_fno-stack-protector) $(VBOX_GCC_fvisibility-hidden) $(VBOX_GCC_fvisibility-inlines-hidden) -fno-rtti $(VBOX_GCC_IPRT_FMT_CHECK) ++ TEMPLATE_VBoxRc_CXXFLAGS = -fno-pie -nostdinc -g $(VBOX_GCC_pipe) $(VBOX_GCC_WERR) $(VBOX_GCC_PEDANTIC_CXX) $(VBOX_GCC32_Wno-variadic-macros) -fno-exceptions $(VBOX_GCC_GC_OPT) $(VBOX_GCC_GC_FP) -mno-sse -mno-mmx -mno-sse2 -mno-3dnow -fno-strict-aliasing $(VBOX_GCC_fno-stack-protector) $(VBOX_GCC_fvisibility-hidden) $(VBOX_GCC_fvisibility-inlines-hidden) $(VBOX_GCC_IPRT_FMT_CHECK) + TEMPLATE_VBoxRc_CFLAGS = -fno-pie -nostdinc -g $(VBOX_GCC_pipe) $(VBOX_GCC_WERR) $(VBOX_GCC_PEDANTIC_C) $(VBOX_GCC32_Wno-variadic-macros) -fno-exceptions $(VBOX_GCC_GC_OPT) $(VBOX_GCC_GC_FP) -mno-sse -mno-mmx -mno-sse2 -mno-3dnow -fno-strict-aliasing $(VBOX_GCC_fno-stack-protector) $(VBOX_GCC_fvisibility-hidden) $(VBOX_GCC_IPRT_FMT_CHECK) + if $(VBOX_GCC32_VERSION_CC) < 30400 + TEMPLATE_VBoxRc_DEFS += RT_WITHOUT_PRAGMA_ONCE +@@ -4500,7 +4498,7 @@ TEMPLATE_VBoxR0_CFLAGS = -fno-pie -nostdinc -g $(VBOX_GCC_pipe) $(V + TEMPLATE_VBoxR0_CXXFLAGS = -fno-pie -nostdinc -g $(VBOX_GCC_pipe) $(VBOX_GCC_WERR) $(VBOX_GCC_PEDANTIC_CXX) \ + $(VBOX_GCC_Wno-variadic-macros) $(VBOX_GCC_R0_OPT) $(VBOX_GCC_R0_FP) -fno-strict-aliasing -fno-exceptions \ + $(VBOX_GCC_fno-stack-protector) -fno-common $(VBOX_GCC_fvisibility-inlines-hidden) $(VBOX_GCC_fvisibility-hidden) \ +- -fno-rtti $(VBOX_GCC_IPRT_FMT_CHECK) ++ $(VBOX_GCC_IPRT_FMT_CHECK) + TEMPLATE_VBoxR0_CFLAGS.amd64 = -m64 -mno-red-zone -mno-sse -mno-mmx -mno-sse2 -mno-3dnow -fasynchronous-unwind-tables -ffreestanding + TEMPLATE_VBoxR0_CXXFLAGS.amd64 = -m64 -mno-red-zone -mno-sse -mno-mmx -mno-sse2 -mno-3dnow -fasynchronous-unwind-tables + TEMPLATE_VBoxR0_CXXFLAGS.freebsd = -ffreestanding +@@ -5028,31 +5026,31 @@ endif # NetBSD + + ifeq ($(KBUILD_TARGET),haiku) + ## The Haiku include directories +-VBOX_HAIKU_SYS_INCS ?= /boot/develop/headers/os/kernel /boot/develop/headers/os/drivers ++VBOX_HAIKU_SYS_INCS ?= /boot/system/develop/headers/os/kernel /boot/system/develop/headers/os/drivers /boot/system/develop/headers/private/shared /boot/system/develop/headers/private/kernel/ + + TEMPLATE_VBOXR0DRV_TOOL = $(VBOX_GCC_TOOL) + TEMPLATE_VBOXR0DRV_LDTOOL = $(VBOX_GCC_TOOL) +-TEMPLATE_VBOXR0DRV_DEFS = _KERNEL_MODE=1 _STRICT_STDC IN_RING0 IN_RT_R0 ++TEMPLATE_VBOXR0DRV_DEFS = _KERNEL _KERNEL_MODE=1 _STRICT_STDC IN_RING0 IN_RT_R0 + if $(VBOX_GCC_VERSION_CC) < 30400 + TEMPLATE_VBOXR0DRV_DEFS += RT_WITHOUT_PRAGMA_ONCE + endif + TEMPLATE_VBOXR0DRV_INCS = $(VBOX_HAIKU_SYS_INCS) + #TODO: sort this out +-TEMPLATE_VBOXR0DRV_LDFLAGS = -shared $(VBOX_GCC_NO_UNDEFINED_R0) -dc -dy -lroot -rpath-link /boot/system/develop/lib/x86 --no-add-needed /boot/system/develop/lib/_KERNEL_ --no-add-needed /boot/system/develop/lib/haiku_version_glue.o +-TEMPLATE_VBOXR0DRV_CFLAGS = -fno-PIC \ ++TEMPLATE_VBOXR0DRV_LDFLAGS = -shared $(VBOX_GCC_NO_UNDEFINED_R0) -nostdlib --no-add-needed /boot/system/develop/lib/_KERNEL_ --no-add-needed /boot/system/develop/lib/haiku_version_glue.o -z max-page-size=0x1000 ++TEMPLATE_VBOXR0DRV_CFLAGS = -fPIC \ + $(VBOX_GCC_WARN) -Wstrict-prototypes $(VBOX_GCC_Wno-pointer-sign) -Wno-sign-compare \ +- $(VBOX_GCC_fno-stack-protector) $(VBOX_GCC_R0_OPT) $(VBOX_GCC_R0_FP) -fno-strict-aliasing -fno-common -Werror-implicit-function-declaration ++ $(VBOX_GCC_fno-stack-protector) $(VBOX_GCC_R0_OPT) $(VBOX_GCC_R0_FP) -fno-strict-aliasing -fno-delete-null-pointer-checks -fno-builtin-fork -fno-builtin-vfork -fno-common -Werror-implicit-function-declaration + TEMPLATE_VBOXR0DRV_CFLAGS.x86 = -mno-sse -mno-mmx -mno-sse2 -mno-3dnow + TEMPLATE_VBOXR0DRV_CFLAGS.x86 = -m32 -mno-sse -mno-mmx -mno-sse2 -mno-3dnow +-TEMPLATE_VBOXR0DRV_CFLAGS.amd64 = -m64 -mno-sse -mno-mmx -mno-sse2 -mno-3dnow \ ++TEMPLATE_VBOXR0DRV_CFLAGS.amd64 = -m64 -mno-sse2 -mno-3dnow \ + -fno-reorder-blocks -ffreestanding -fno-asynchronous-unwind-tables -funit-at-a-time \ + -Wno-sign-compare +-TEMPLATE_VBOXR0DRV_CXXFLAGS = -fno-PIC -Wpointer-arith \ ++TEMPLATE_VBOXR0DRV_CXXFLAGS = -fPIC -Wpointer-arith \ + -Wshadow -Wuninitialized -Wunused-function -Wunused-label -Wunused-value -Wunused-variable \ +- -Wformat \ +- -O2 -nodefaultlibs -fno-omit-frame-pointer -fno-strict-aliasing -fno-common -fno-exceptions -fno-rtti +-TEMPLATE_VBOXR0DRV_CXXFLAGS.x86 = $(TEMPLATE_VBOXR0DRV_CFLAGS.x86) -fno-exceptions -fno-rtti +-TEMPLATE_VBOXR0DRV_CXXFLAGS.amd64 = $(TEMPLATE_VBOXR0DRV_CFLAGS.amd64) -fno-exceptions -fno-rtti ++ -Wformat -D_KERNEL -D_KERNEL_MODE=1 \ ++ -O2 -nodefaultlibs -fno-omit-frame-pointer -fno-strict-aliasing -fno-common -fno-delete-null-pointer-checks -fno-builtin-fork -fno-builtin-vfork -ffreestanding -finline ++TEMPLATE_VBOXR0DRV_CXXFLAGS.x86 = $(TEMPLATE_VBOXR0DRV_CFLAGS.x86) -fno-delete-null-pointer-checks -fno-builtin-fork -fno-builtin-vfork ++TEMPLATE_VBOXR0DRV_CXXFLAGS.amd64 = $(TEMPLATE_VBOXR0DRV_CFLAGS.amd64) -fno-delete-null-pointer-checks -fno-builtin-fork -fno-builtin-vfork + endif # Haiku + + ifdef VBOX_WITH_VBOXDRV +@@ -5187,8 +5185,7 @@ TEMPLATE_VBOXR3EXE_TOOL = $(VBOX_GCC_TOOL) + if $(VBOX_GCC_VERSION_CC) < 30400 + TEMPLATE_VBOXR3EXE_DEFS += RT_WITHOUT_PRAGMA_ONCE + endif +-TEMPLATE_VBOXR3EXE_CXXFLAGS = -g $(VBOX_GCC_pipe) $(VBOX_GCC_PEDANTIC_CXX) $(VBOX_GCC_Wno-variadic-macros) $(VBOX_GCC_OPT) \ +- $(VBOX_GCC_FP) -fno-strict-aliasing $(VBOX_GCC_fvisibility-hidden) $(VBOX_GCC_fvisibility-inlines-hidden) $(VBOX_GCC_IPRT_FMT_CHECK) ++TEMPLATE_VBOXR3EXE_CXXFLAGS = -g + ifdef VBOX_WITH_NO_GCC_WARNING_POLICY + TEMPLATE_VBOXR3EXE_CXXFLAGS += $(VBOX_GCC_WERR) + endif +@@ -5198,7 +5195,7 @@ TEMPLATE_VBOXR3EXE_CXXFLAGS.sparc32 = -m32 + TEMPLATE_VBOXR3EXE_CXXFLAGS.sparc64 = -m64 + TEMPLATE_VBOXR3EXE_CXXFLAGS.kprofile = -finstrument-functions + TEMPLATE_VBOXR3EXE_CXXFLAGS.debug = $(VBOX_GCC_SANITIZER_FLAGS) +-TEMPLATE_VBOXR3EXE_CFLAGS = -g $(VBOX_GCC_pipe) $(VBOX_GCC_PEDANTIC_C) $(VBOX_GCC_Wno-variadic-macros) $(VBOX_GCC_OPT) $(VBOX_GCC_FP) -fno-strict-aliasing $(VBOX_GCC_fvisibility-hidden) $(VBOX_GCC_IPRT_FMT_CHECK) ++TEMPLATE_VBOXR3EXE_CFLAGS = -g + ifdef VBOX_WITH_NO_GCC_WARNING_POLICY + TEMPLATE_VBOXR3EXE_CFLAGS += $(VBOX_GCC_WERR) + endif +@@ -5255,11 +5252,11 @@ TEMPLATE_VBOXR3EXE_TOOL = GXX3 + TEMPLATE_VBOXR3EXE_POST_CMDS = $(VBOX_HAIKU_XRES_SETVER_CMDS) + TEMPLATE_VBOXR3EXE_LIBS = network iconv stdc++ supc++ + TEMPLATE_VBOXR3EXE_LIBPATH += \ +- /boot/common/lib ++ /boot/system/develop/lib + # Haiku uses PIC by default... +-TEMPLATE_VBOXR3EXE_CFLAGS += -fno-pic +-TEMPLATE_VBOXR3EXE_CXXFLAGS += -fno-pic +-TEMPLATE_VBOXR3EXE_LDFLAGS += -fno-pic ++TEMPLATE_VBOXR3EXE_CFLAGS += ++TEMPLATE_VBOXR3EXE_CXXFLAGS += ++TEMPLATE_VBOXR3EXE_LDFLAGS += + else if1of ($(KBUILD_TARGET), freebsd openbsd) + TEMPLATE_VBOXR3EXE_TOOL = GXX3 + TEMPLATE_VBOXR3EXE_LIBS = pthread +@@ -5318,10 +5315,10 @@ ifn1of ($(KBUILD_TARGET), darwin win os2) + endif + ifeq ($(KBUILD_TARGET),haiku) + # Haiku uses PIC by default... +- TEMPLATE_VBOXR3_CFLAGS = $(TEMPLATE_VBOXR3EXE_CFLAGS) -fno-pic +- TEMPLATE_VBOXR3_CXXFLAGS = $(TEMPLATE_VBOXR3EXE_CXXFLAGS) -fno-pic +- TEMPLATE_VBOXR3_PCHFLAGS = $(TEMPLATE_VBOXR3EXE_PCHFLAGS) -fno-pic +- TEMPLATE_VBOXR3_LDFLAGS = $(TEMPLATE_VBOXR3EXE_LDFLAGS) -fno-pic ++ TEMPLATE_VBOXR3_CFLAGS = $(TEMPLATE_VBOXR3EXE_CFLAGS) ++ TEMPLATE_VBOXR3_CXXFLAGS = $(TEMPLATE_VBOXR3EXE_CXXFLAGS) ++ TEMPLATE_VBOXR3_PCHFLAGS = $(TEMPLATE_VBOXR3EXE_PCHFLAGS) ++ TEMPLATE_VBOXR3_LDFLAGS = $(TEMPLATE_VBOXR3EXE_LDFLAGS) + endif + + # +@@ -7133,7 +7130,7 @@ ifeq ($(KBUILD_TARGET),win) + else # the gcc guys + TEMPLATE_VBOXGUESTR3EXE_EXTENDS = VBOXR3EXE + TEMPLATE_VBOXGUESTR3EXE_TOOL := $(subst GXX,GCC,$(TEMPLATE_VBOXR3EXE_TOOL)) +- TEMPLATE_VBOXGUESTR3EXE_CXXFLAGS = $(TEMPLATE_VBOXR3EXE_CXXFLAGS) -fno-exceptions -fno-rtti ++ TEMPLATE_VBOXGUESTR3EXE_CXXFLAGS = $(TEMPLATE_VBOXR3EXE_CXXFLAGS) -fno-exceptions + # Do not inherit sanitizer flags from VBOXR3EXE in guest executables. Deal with them separately. + TEMPLATE_VBOXGUESTR3EXE_CXXFLAGS.debug = $(NO_SUCH_VARIABLE) + TEMPLATE_VBOXGUESTR3EXE_CFLAGS.debug = $(NO_SUCH_VARIABLE) +diff --git a/src/VBox/Additions/common/VBoxGuest/Makefile.kmk b/src/VBox/Additions/common/VBoxGuest/Makefile.kmk +index 81b488a..d71ecfb 100644 +--- a/src/VBox/Additions/common/VBoxGuest/Makefile.kmk ++++ b/src/VBox/Additions/common/VBoxGuest/Makefile.kmk +@@ -133,6 +133,7 @@ if1of ($(KBUILD_TARGET), darwin freebsd haiku netbsd os2 solaris win) + VBoxDev_NAME = vboxdev + VBoxDev_DEFS = VBOX_SVN_REV=$(VBOX_SVN_REV) _KERNEL_MODE=1 VBGL_VBOXGUEST VBOX_WITH_HGCM IN_RING0 + VBoxDev_SOURCES = VBoxDev-haiku.c VBoxGuest-haiku-stubs.c ++ + endif + else # OS/2: + # The library order is crucial, so a bit of trickery is necessary. +diff --git a/src/VBox/Additions/common/VBoxGuest/VBoxDev-haiku.c b/src/VBox/Additions/common/VBoxGuest/VBoxDev-haiku.c +index 450898e..ab2ee5e 100644 +--- a/src/VBox/Additions/common/VBoxGuest/VBoxDev-haiku.c ++++ b/src/VBox/Additions/common/VBoxGuest/VBoxDev-haiku.c +@@ -69,10 +69,13 @@ + #include "VBoxGuestInternal.h" + #include + #include ++#include + #include + #include + #include + #include ++#include ++#include + + #define DRIVER_NAME "vboxdev" + #define DEVICE_NAME "misc/vboxguest" +@@ -113,7 +116,7 @@ static status_t vgdrvHaikuOpen(const char *name, uint32 flags, void **cookie) + return B_OK; + } + +- LogRel((DRIVER_NAME ":vgdrvHaikuOpen: failed. rc=%d\n", rc)); ++ Log((DRIVER_NAME ":vgdrvHaikuOpen: failed. rc=%d\n", rc)); + return RTErrConvertToErrno(rc); + } + +@@ -184,6 +187,9 @@ static status_t vgdrvHaikuFree(void *cookie) + static status_t vgdrvHaikuIOCtl(void *cookie, uint32 op, void *data, size_t len) + { + PVBOXGUESTSESSION pSession = (PVBOXGUESTSESSION)cookie; ++ PVBGLREQHDR pHdr = NULL; ++ VBGLREQHDR Hdr; ++ size_t cbBuf = 0; + int rc; + Log(("vgdrvHaikuIOCtl: cookie=%p op=0x%08x data=%p len=%lu)\n", cookie, op, data, len)); + +@@ -192,7 +198,19 @@ static status_t vgdrvHaikuIOCtl(void *cookie, uint32 op, void *data, size_t len) + */ + if (RT_UNLIKELY(!VALID_PTR(pSession))) + return EINVAL; +- ++ /* ++ * Read the header. ++ */ ++ if (RT_UNLIKELY(user_memcpy(&Hdr, data, sizeof(Hdr)) < 0)) ++ { ++ Log(("vgdrvHaikuIOCtl: copy_from_user(,%#lx,) failed; uCmd=%#x\n", data, op)); ++ return EFAULT; ++ } ++ if (RT_UNLIKELY(Hdr.uVersion != VBGLREQHDR_VERSION)) ++ { ++ Log(("vgdrvHaikuIOCtl: bad header version %#x; uCmd=%#x\n", Hdr.uVersion, op)); ++ return EINVAL; ++ } + /* + * Validate the request wrapper. + */ +@@ -204,8 +222,8 @@ static status_t vgdrvHaikuIOCtl(void *cookie, uint32 op, void *data, size_t len) + return ENOTTY; + } + #endif +- +- if (RT_UNLIKELY(len > _1M * 16)) ++ cbBuf = RT_MAX(Hdr.cbIn, Hdr.cbOut); ++ if (RT_UNLIKELY(cbBuf > _1M * 16)) + { + dprintf(DRIVER_NAME ": vgdrvHaikuIOCtl: bad size %#x; pArg=%p Cmd=%lu.\n", (unsigned)len, data, op); + return EINVAL; +@@ -214,50 +232,43 @@ static status_t vgdrvHaikuIOCtl(void *cookie, uint32 op, void *data, size_t len) + /* + * Read the request. + */ +- void *pvBuf = NULL; +- if (RT_LIKELY(len > 0)) ++ if (RT_LIKELY(cbBuf > 0)) + { +- pvBuf = RTMemTmpAlloc(len); +- if (RT_UNLIKELY(!pvBuf)) ++ pHdr = RTMemTmpAlloc(cbBuf); ++ if (RT_UNLIKELY(!pHdr)) + { +- LogRel((DRIVER_NAME ":vgdrvHaikuIOCtl: RTMemTmpAlloc failed to alloc %d bytes.\n", len)); ++ Log((DRIVER_NAME ":vgdrvHaikuIOCtl: RTMemTmpAlloc failed to alloc %d bytes.\n", len)); + return ENOMEM; + } + + /** @todo r=ramshankar: replace with RTR0MemUserCopyFrom() */ +- rc = user_memcpy(pvBuf, data, len); +- if (RT_UNLIKELY(rc < 0)) ++ if (RT_UNLIKELY(user_memcpy((void*)pHdr, data, cbBuf) < 0)) + { +- RTMemTmpFree(pvBuf); +- LogRel((DRIVER_NAME ":vgdrvHaikuIOCtl: user_memcpy failed; pvBuf=%p data=%p op=%d. rc=%d\n", pvBuf, data, op, rc)); ++ RTMemTmpFree(pHdr); ++ Log((DRIVER_NAME ":vgdrvHaikuIOCtl: user_memcpy failed; pHdr=%p data=%p op=%d\n", pHdr, data, op)); + return EFAULT; + } +- if (RT_UNLIKELY(!VALID_PTR(pvBuf))) +- { +- RTMemTmpFree(pvBuf); +- LogRel((DRIVER_NAME ":vgdrvHaikuIOCtl: pvBuf invalid pointer %p\n", pvBuf)); +- return EINVAL; +- } ++ + } + Log(("vgdrvHaikuIOCtl: pSession=%p pid=%d.\n", pSession,(int)RTProcSelf())); + + /* + * Process the IOCtl. + */ +- size_t cbDataReturned; +- rc = VGDrvCommonIoCtl(op, &g_DevExt, pSession, pvBuf, len, &cbDataReturned); ++ rc = VGDrvCommonIoCtl(op, &g_DevExt, pSession, pHdr, cbBuf); ++ + if (RT_SUCCESS(rc)) + { + rc = 0; +- if (RT_UNLIKELY(cbDataReturned > len)) ++ uint32_t cbOut = pHdr->cbOut; ++ if (RT_UNLIKELY(cbOut > cbBuf)) + { +- Log(("vgdrvHaikuIOCtl: too much output data %d expected %d\n", cbDataReturned, len)); +- cbDataReturned = len; ++ Log(("vgdrvHaikuIOCtl: too much output data %d expected %d\n", cbOut, cbBuf)); ++ cbOut = len; + } +- if (cbDataReturned > 0) ++ if (cbOut > 0) + { +- rc = user_memcpy(data, pvBuf, cbDataReturned); +- if (RT_UNLIKELY(rc < 0)) ++ if (RT_FAILURE(user_memcpy((void*)data, pHdr, cbOut))) + { + Log(("vgdrvHaikuIOCtl: user_memcpy failed; pvBuf=%p pArg=%p Cmd=%lu. rc=%d\n", pvBuf, data, op, rc)); + rc = EFAULT; +@@ -269,11 +280,10 @@ static status_t vgdrvHaikuIOCtl(void *cookie, uint32 op, void *data, size_t len) + Log(("vgdrvHaikuIOCtl: VGDrvCommonIoCtl failed. rc=%d\n", rc)); + rc = EFAULT; + } +- RTMemTmpFree(pvBuf); ++ RTMemTmpFree(pHdr); + return rc; + } + +- + /** + * Driver select hook. + * +diff --git a/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku-stubs.c b/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku-stubs.c +index 074d7af..037c004 100644 +--- a/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku-stubs.c ++++ b/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku-stubs.c +@@ -63,6 +63,7 @@ + #include "VBoxGuest-haiku.h" + #include "VBoxGuestInternal.h" + #include ++#include + #include + #include + #include +@@ -347,17 +348,13 @@ RTDECL(PRTLOGGER) RTLogRelGetDefaultInstance(void) + { + return g_VBoxGuest->_RTLogRelGetDefaultInstance(); + } +-RTDECL(PRTLOGGER) RTLogRelGetDefaultInstance(uint32_t fFlags, uint32_t iGroup) +-{ +- return g_VBoxGuest->_RTLogRelGetDefaultInstanceEx(fFlags, iGroup); +-} + RTDECL(int) RTErrConvertToErrno(int iErr) + { + return g_VBoxGuest->_RTErrConvertToErrno(iErr); + } +-int VGDrvCommonIoCtl(unsigned iFunction, PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession, void *pvData, size_t cbData, size_t *pcbDataReturned) ++int VGDrvCommonIoCtl(uintptr_t iFunction, PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession, PVBGLREQHDR pReqHdr, size_t cbReq) + { +- return g_VBoxGuest->_VGDrvCommonIoCtl(iFunction, pDevExt, pSession, pvData, cbData, pcbDataReturned); ++ return g_VBoxGuest->_VGDrvCommonIoCtl(iFunction, pDevExt, pSession, pReqHdr, cbReq); + } + int VGDrvCommonCreateUserSession(PVBOXGUESTDEVEXT pDevExt, uint32_t fRequestor, PVBOXGUESTSESSION *ppSession) + { +@@ -367,17 +364,9 @@ void VGDrvCommonCloseSession(PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSessio + { + g_VBoxGuest->_VGDrvCommonCloseSession(pDevExt, pSession); + } +-void* VBoxGuestIDCOpen(uint32_t *pu32Version) ++int VBoxGuestIDC(void *pvSession, uintptr_t uReq, PVBGLREQHDR pReqHdr, size_t cbReq) + { +- return g_VBoxGuest->_VBoxGuestIDCOpen(pu32Version); +-} +-int VBoxGuestIDCClose(void *pvSession) +-{ +- return g_VBoxGuest->_VBoxGuestIDCClose(pvSession); +-} +-int VBoxGuestIDCCall(void *pvSession, unsigned iCmd, void *pvData, size_t cbData, size_t *pcbDataReturned) +-{ +- return g_VBoxGuest->_VBoxGuestIDCCall(pvSession, iCmd, pvData, cbData, pcbDataReturned); ++ return g_VBoxGuest->_VBoxGuestIDC(pvSession, uReq, pReqHdr, cbReq); + } + RTDECL(void) RTAssertMsg1Weak(const char *pszExpr, unsigned uLine, const char *pszFile, const char *pszFunction) + { +@@ -458,4 +447,7 @@ void RTHeapSimpleFree(RTHEAPSIMPLE Heap, void *pv) + { + g_VBoxGuest->_RTHeapSimpleFree(Heap, pv); + } +- ++int RTStrCopy(char *pszDst, size_t cbDst, const char *pszSrc) ++{ ++ return g_VBoxGuest->_RTStrCopy(pszDst, cbDst, pszSrc); ++} +diff --git a/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku.c b/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku.c +index 0cedd51..470d963 100644 +--- a/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku.c ++++ b/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku.c +@@ -63,6 +63,7 @@ + #include + #include + #include ++#define _KERNEL_MODE 1 + #include + #include + +@@ -70,6 +71,7 @@ + #include "VBoxGuestInternal.h" + #include + #include ++#include + #include + #include + #include +@@ -77,7 +79,7 @@ + #include + #include + #include +- ++#include + + /********************************************************************************************************************************* + * Defined Constants And Macros * +@@ -91,10 +93,13 @@ + /* + * IRQ related functions. + */ ++RT_C_DECLS_BEGIN + static void vgdrvHaikuRemoveIRQ(void *pvState); + static int vgdrvHaikuAddIRQ(void *pvState); + static int32 vgdrvHaikuISR(void *pvState); + ++int IDCCall(void *pvSession, uintptr_t uReq, PVBGLREQHDR pReqHdr, size_t cbReq); ++RT_C_DECLS_END + + /********************************************************************************************************************************* + * Global Variables * +@@ -195,9 +200,7 @@ static struct vboxguest_module_info g_VBoxGuest = + VGDrvCommonIoCtl, + VGDrvCommonCreateUserSession, + VGDrvCommonCloseSession, +- VBoxGuestIDCOpen, +- VBoxGuestIDCClose, +- VBoxGuestIDCCall, ++ IDCCall, + RTAssertMsg1Weak, + RTAssertMsg2Weak, + RTAssertMsg2WeakV, +@@ -216,7 +219,8 @@ static struct vboxguest_module_info g_VBoxGuest = + RTHeapOffsetAlloc, + RTHeapSimpleAlloc, + RTHeapOffsetFree, +- RTHeapSimpleFree ++ RTHeapSimpleFree, ++ RTStrCopy + }; + + #if 0 +@@ -359,6 +363,49 @@ bool VGDrvNativeProcessOption(PVBOXGUESTDEVEXT pDevExt, const char *pszName, con + return false; + } + ++/** ++ * @note This code is duplicated on other platforms with variations, so please ++ * keep them all up to date when making changes! ++ */ ++int IDCCall(void *pvSession, uintptr_t uReq, PVBGLREQHDR pReqHdr, size_t cbReq) ++{ ++ /* ++ * Simple request validation (common code does the rest). ++ */ ++ int rc; ++ if ( RT_VALID_PTR(pReqHdr) ++ && cbReq >= sizeof(*pReqHdr)) ++ { ++ /* ++ * All requests except the connect one requires a valid session. ++ */ ++ PVBOXGUESTSESSION pSession = (PVBOXGUESTSESSION)pvSession; ++ if (pSession) ++ { ++ if ( RT_VALID_PTR(pSession) ++ && pSession->pDevExt == &g_DevExt) ++ rc = VGDrvCommonIoCtl(uReq, &g_DevExt, pSession, pReqHdr, cbReq); ++ else ++ rc = VERR_INVALID_HANDLE; ++ } ++ else if (uReq == VBGL_IOCTL_IDC_CONNECT) ++ { ++ rc = VGDrvCommonCreateKernelSession(&g_DevExt, &pSession); ++ if (RT_SUCCESS(rc)) ++ { ++ rc = VGDrvCommonIoCtl(uReq, &g_DevExt, pSession, pReqHdr, cbReq); ++ if (RT_FAILURE(rc)) ++ VGDrvCommonCloseSession(&g_DevExt, pSession); ++ } ++ } ++ else ++ rc = VERR_INVALID_HANDLE; ++ } ++ else ++ rc = VERR_INVALID_POINTER; ++ return rc; ++} ++ + + /** + * Sets IRQ for VMMDev. +@@ -516,7 +563,6 @@ static status_t vgdrvHaikuProbe(pci_info *pDevice) + return ENXIO; + } + +- + status_t init_module(void) + { + status_t err = B_ENTRY_NOT_FOUND; +@@ -572,7 +618,3 @@ _EXPORT module_info *modules[] = + (module_info *)&g_VBoxGuest, + NULL + }; +- +-/* Common code that depend on g_DevExt. */ +-#include "VBoxGuestIDC-unix.c.h" +- +diff --git a/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku.h b/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku.h +index 12d8cf0..b758e05 100644 +--- a/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku.h ++++ b/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku.h +@@ -194,13 +194,10 @@ struct vboxguest_module_info + PRTLOGGER(*_RTLogRelGetDefaultInstance)(void); + PRTLOGGER(*_RTLogRelGetDefaultInstanceEx)(uint32_t fFlagsAndGroup); + int (*_RTErrConvertToErrno)(int iErr); +- int (*_VGDrvCommonIoCtl)(unsigned iFunction, PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession, +- void *pvData, size_t cbData, size_t *pcbDataReturned); ++ int (*_VGDrvCommonIoCtl)(uintptr_t iFunction, PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession, PVBGLREQHDR pReqHdr, size_t cbReq); + int (*_VGDrvCommonCreateUserSession)(PVBOXGUESTDEVEXT pDevExt, uint32_t fRequestor, PVBOXGUESTSESSION *ppSession); + void (*_VGDrvCommonCloseSession)(PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSION pSession); +- void* (*_VBoxGuestIDCOpen)(uint32_t *pu32Version); +- int (*_VBoxGuestIDCClose)(void *pvSession); +- int (*_VBoxGuestIDCCall)(void *pvSession, unsigned iCmd, void *pvData, size_t cbData, size_t *pcbDataReturned); ++ int (*_VBoxGuestIDC)(void *pvSession, uintptr_t uReq, PVBGLREQHDR pReqHdr, size_t cbReq); + void (*_RTAssertMsg1Weak)(const char *pszExpr, unsigned uLine, const char *pszFile, const char *pszFunction); + void (*_RTAssertMsg2Weak)(const char *pszFormat, ...); + void (*_RTAssertMsg2WeakV)(const char *pszFormat, va_list va); +@@ -220,6 +217,7 @@ struct vboxguest_module_info + void* (*_RTHeapSimpleAlloc)(RTHEAPSIMPLE Heap, size_t cb, size_t cbAlignment); + void (*_RTHeapOffsetFree)(RTHEAPOFFSET hHeap, void *pv); + void (*_RTHeapSimpleFree)(RTHEAPSIMPLE Heap, void *pv); ++ int (*_RTStrCopy)(char *pszDst, size_t cbDst, const char *pszSrc); + }; + + +diff --git a/src/VBox/Additions/common/VBoxGuest/VBoxGuest.cpp b/src/VBox/Additions/common/VBoxGuest/VBoxGuest.cpp +index f2f26e1..b279378 100644 +--- a/src/VBox/Additions/common/VBoxGuest/VBoxGuest.cpp ++++ b/src/VBox/Additions/common/VBoxGuest/VBoxGuest.cpp +@@ -78,6 +78,9 @@ + # include + #endif + ++#include ++#include ++ + + /********************************************************************************************************************************* + * Defined Constants And Macros * +@@ -3977,6 +3980,7 @@ static int vgdrvIoCtl_SetCapabilities(PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSESSIO + return rc; + } + ++ + /** @} */ + + +@@ -3999,8 +4003,7 @@ int VGDrvCommonIoCtl(uintptr_t iFunction, PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSE + { + uintptr_t const iFunctionStripped = VBGL_IOCTL_CODE_STRIPPED(iFunction); + int rc; +- +- LogFlow(("VGDrvCommonIoCtl: iFunction=%#x pDevExt=%p pSession=%p pReqHdr=%p cbReq=%zu\n", ++ Log(("VGDrvCommonIoCtl: iFunction=%#x pDevExt=%p pSession=%p pReqHdr=%p cbReq=%zu\n", + iFunction, pDevExt, pSession, pReqHdr, cbReq)); + + /* +@@ -4283,11 +4286,11 @@ int VGDrvCommonIoCtl(uintptr_t iFunction, PVBOXGUESTDEVEXT pDevExt, PVBOXGUESTSE + } + else + { +- Log(("VGDrvCommonIoCtl: uType=%#x, expected default (ioctl=%#x)\n", pReqHdr->uType, iFunction)); ++ //LogRel(("VGDrvCommonIoCtl: uType=%#x, expected default (ioctl=%#x)\n", pReqHdr->uType, iFunction)); + return VERR_INVALID_PARAMETER; + } + +- LogFlow(("VGDrvCommonIoCtl: returns %Rrc (req: rc=%Rrc cbOut=%#x)\n", rc, pReqHdr->rc, pReqHdr->cbOut)); ++ //LogRel("VGDrvCommonIoCtl: returns %Rrc (req: rc=%Rrc cbOut=%#x)\n", rc, pReqHdr->rc, pReqHdr->cbOut)); + return rc; + } + +diff --git a/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibIdc-unix.cpp b/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibIdc-unix.cpp +index 92979d2..d8c0d9d 100644 +--- a/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibIdc-unix.cpp ++++ b/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibIdc-unix.cpp +@@ -34,7 +34,6 @@ + *********************************************************************************************************************************/ + #include "VBoxGuestR0LibInternal.h" + +- + int VBOXCALL vbglR0IdcNativeOpen(PVBGLIDCHANDLE pHandle, PVBGLIOCIDCCONNECT pReq) + { + RT_NOREF(pHandle); +diff --git a/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibInit.cpp b/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibInit.cpp +index a135ae6..791f5fe 100644 +--- a/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibInit.cpp ++++ b/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibInit.cpp +@@ -39,6 +39,11 @@ + #include + #include + ++#undef dprintf ++ ++#include ++#include ++#include + + /********************************************************************************************************************************* + * Global Variables * +@@ -84,17 +89,24 @@ static void vbglR0QueryHostVersion(void) + */ + static int vbglR0QueryDriverInfo(void) + { ++ dprintf("In vbglR0QueryDriverInfo\n"); + # ifdef VBGLDATA_USE_FAST_MUTEX ++ dprintf("Fast Mutex\n"); ++ + int rc = RTSemFastMutexRequest(g_vbgldata.hMtxIdcSetup); + # else ++ dprintf("Reg Mutex\n"); ++ + int rc = RTSemMutexRequest(g_vbgldata.hMtxIdcSetup, RT_INDEFINITE_WAIT); + # endif + if (RT_SUCCESS(rc)) + { ++ dprintf("Acquired Driver Mutex\n"); + if (g_vbgldata.status == VbglStatusReady) + { /* likely */ } + else + { ++ dprintf("Opening Idc\n"); + rc = VbglR0IdcOpen(&g_vbgldata.IdcHandle, + VBGL_IOC_VERSION /*uReqVersion*/, + VBGL_IOC_VERSION & UINT32_C(0xffff0000) /*uMinVersion*/, +@@ -104,23 +116,26 @@ static int vbglR0QueryDriverInfo(void) + /* + * Try query the port info. + */ ++ dprintf("Query Idc\n"); + VBGLIOCGETVMMDEVIOINFO PortInfo; + RT_ZERO(PortInfo); + VBGLREQHDR_INIT(&PortInfo.Hdr, GET_VMMDEV_IO_INFO); ++ dprintf("Call Idc\n"); + rc = VbglR0IdcCall(&g_vbgldata.IdcHandle, VBGL_IOCTL_GET_VMMDEV_IO_INFO, &PortInfo.Hdr, sizeof(PortInfo)); + if (RT_SUCCESS(rc)) + { +- dprintf(("Port I/O = 0x%04x, MMIO = %p\n", PortInfo.u.Out.IoPort, PortInfo.u.Out.pvVmmDevMapping)); ++ dprintf("Port I/O = 0x%04x, MMIO = %p\n", PortInfo.u.Out.IoPort, PortInfo.u.Out.pvVmmDevMapping); + + g_vbgldata.portVMMDev = PortInfo.u.Out.IoPort; + g_vbgldata.pVMMDevMemory = (VMMDevMemory *)PortInfo.u.Out.pvVmmDevMapping; + g_vbgldata.status = VbglStatusReady; ++ dprintf("Query Host Version\n"); + + vbglR0QueryHostVersion(); + } + } + +- dprintf(("vbglQueryDriverInfo rc = %Rrc\n", rc)); ++ dprintf("vbglQueryDriverInfo rc = %d\n", rc); + } + + # ifdef VBGLDATA_USE_FAST_MUTEX +@@ -129,6 +144,8 @@ static int vbglR0QueryDriverInfo(void) + RTSemMutexRelease(g_vbgldata.hMtxIdcSetup); + # endif + } ++ dprintf("Finished driver info %d\n", rc); ++ + return rc; + } + #endif /* !VBGL_VBOXGUEST */ +@@ -167,11 +184,11 @@ static int vbglR0InitCommon(void) + rc = VbglR0PhysHeapInit(); + if (RT_SUCCESS(rc)) + { +- dprintf(("vbglR0InitCommon: returns rc = %d\n", rc)); ++ dprintf("vbglR0InitCommon: returns rc = %d\n", rc); + return rc; + } + +- LogRel(("vbglR0InitCommon: VbglR0PhysHeapInit failed: rc=%Rrc\n", rc)); ++ Log(("vbglR0InitCommon: VbglR0PhysHeapInit failed: rc=%Rrc\n", rc)); + g_vbgldata.status = VbglStatusNotInitialized; + return rc; + } +@@ -190,7 +207,7 @@ DECLR0VBGL(int) VbglR0InitPrimary(RTIOPORT portVMMDev, VMMDevMemory *pVMMDevMemo + int rc; + + # ifdef RT_OS_WINDOWS /** @todo r=bird: this doesn't make sense. Is there something special going on on windows? */ +- dprintf(("vbglInit: starts g_vbgldata.status %d\n", g_vbgldata.status)); ++ dprintf("vbglInit: starts g_vbgldata.status %d\n", g_vbgldata.status); + + if ( g_vbgldata.status == VbglStatusInitializing + || g_vbgldata.status == VbglStatusReady) +@@ -199,7 +216,7 @@ DECLR0VBGL(int) VbglR0InitPrimary(RTIOPORT portVMMDev, VMMDevMemory *pVMMDevMemo + return VINF_SUCCESS; + } + # else +- dprintf(("vbglInit: starts\n")); ++ dprintf("vbglInit: starts\n"); + # endif + + rc = vbglR0InitCommon(); +@@ -238,22 +255,31 @@ DECLR0VBGL(int) VbglR0InitClient(void) + return VINF_SUCCESS; + } + ++ dprintf("Init Common\n"); + rc = vbglR0InitCommon(); ++ dprintf("Init Common complete\n"); + if (RT_SUCCESS(rc)) + { ++ + # ifdef VBGLDATA_USE_FAST_MUTEX ++ dprintf("Mutex create fast\n"); + rc = RTSemFastMutexCreate(&g_vbgldata.hMtxIdcSetup); + # else ++ dprintf("Mutex create\n"); + rc = RTSemMutexCreate(&g_vbgldata.hMtxIdcSetup); + # endif ++ dprintf("Mutex create complete %d\n", rc); + if (RT_SUCCESS(rc)) + { ++ dprintf("Query drivers\n"); + /* Try to obtain VMMDev port via IOCTL to VBoxGuest main driver. */ + vbglR0QueryDriverInfo(); + + # ifdef VBOX_WITH_HGCM ++ dprintf("HGCM Init\n"); + rc = VbglR0HGCMInit(); + # endif ++ dprintf("Query drivers complete\n"); + if (RT_SUCCESS(rc)) + return VINF_SUCCESS; + +@@ -267,6 +293,7 @@ DECLR0VBGL(int) VbglR0InitClient(void) + } + vbglR0TerminateCommon(); + } ++ dprintf("Terminating on error\n"); + + return rc; + } +diff --git a/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibPhysHeap.cpp b/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibPhysHeap.cpp +index f00e6ec..af8dbcd 100644 +--- a/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibPhysHeap.cpp ++++ b/src/VBox/Additions/common/VBoxGuest/lib/VBoxGuestR0LibPhysHeap.cpp +@@ -322,7 +322,7 @@ static VBGLPHYSHEAPBLOCK *vbglPhysHeapChunkAlloc (uint32_t cbSize) + + if (!pChunk) + { +- LogRel(("vbglPhysHeapChunkAlloc: failed to alloc %u contiguous bytes.\n", cbSize)); ++ Log(("vbglPhysHeapChunkAlloc: failed to alloc %u contiguous bytes.\n", cbSize)); + return NULL; + } + +diff --git a/src/VBox/Additions/haiku/SharedFolders/Makefile.kmk b/src/VBox/Additions/haiku/SharedFolders/Makefile.kmk +index 9b79a21..4369b4c 100644 +--- a/src/VBox/Additions/haiku/SharedFolders/Makefile.kmk ++++ b/src/VBox/Additions/haiku/SharedFolders/Makefile.kmk +@@ -62,7 +62,7 @@ endif + # + vboxsf_TEMPLATE = VBOXGUESTR0 + vboxsf_DEFS = \ +- MODULE IN_RT_R0 VBOXGUEST VBOX_WITH_HGCM \ ++ MODULE IN_RT_R0 VBOXGUEST VBOX_WITH_HGCM _KERNEL_MODE=1 \ + KBUILD_MODNAME=KBUILD_STR\(vboxsf\) \ + KBUILD_BASENAME=KBUILD_STR\(vboxsf\) + vboxsf_INCS = \ +@@ -72,8 +72,10 @@ vboxsf_SOURCES = \ + vboxsf.c \ + vnode_cache.cpp \ + $(PATH_ROOT)/src/VBox/Additions/common/VBoxGuest/VBoxGuest-haiku-stubs.c ++ + vboxsf_LIBS = \ +- $(VBOX_LIB_VBGL_R0) ++ $(VBOX_LIB_VBGL_R0) \ ++ $(VBOX_LIB_IPRT_GUEST_R0) + + include $(KBUILD_PATH)/subfooter.kmk + +diff --git a/src/VBox/Additions/haiku/SharedFolders/OpenHashTable.h b/src/VBox/Additions/haiku/SharedFolders/OpenHashTable.h +deleted file mode 100644 +index da9ed04..0000000 +--- a/src/VBox/Additions/haiku/SharedFolders/OpenHashTable.h ++++ /dev/null +@@ -1,505 +0,0 @@ +-/* $Id: OpenHashTable.h $ */ +-/** @file +- * OpenHashTable, Haiku Guest Additions. +- */ +- +-/* +- * Copyright (C) 2012-2020 Oracle Corporation +- * +- * This file is part of VirtualBox Open Source Edition (OSE), as +- * available from http://www.virtualbox.org. This file is free software; +- * you can redistribute it and/or modify it under the terms of the GNU +- * General Public License (GPL) as published by the Free Software +- * Foundation, in version 2 as it comes in the "COPYING" file of the +- * VirtualBox OSE distribution. VirtualBox OSE is distributed in the +- * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind. +- */ +- +-/* +- * This code is based on: +- * +- * VirtualBox Guest Additions for Haiku. +- * +- * Copyright 2007, Hugo Santos. All Rights Reserved. +- * Distributed under the terms of the MIT License. +- */ +- +-#ifndef GA_INCLUDED_SRC_haiku_SharedFolders_OpenHashTable_h +-#define GA_INCLUDED_SRC_haiku_SharedFolders_OpenHashTable_h +-#ifndef RT_WITHOUT_PRAGMA_ONCE +-# pragma once +-#endif +- +- +-#include +-#include +-#include +- +-#ifdef _KERNEL_MODE +-# include +-# include "kernel_cpp.h" +-#endif +- +-/*! +- The Definition template must have four methods: `HashKey', `Hash', +- `Compare' and `GetLink;. It must also define several types as shown in the +- following example: +- +- struct Foo { +- int bar; +- +- Foo* fNext; +- }; +- +- struct HashTableDefinition { +- typedef int KeyType; +- typedef Foo ValueType; +- +- size_t HashKey(int key) const +- { +- return key >> 1; +- } +- +- size_t Hash(Foo* value) const +- { +- return HashKey(value->bar); +- } +- +- bool Compare(int key, Foo* value) const +- { +- return value->bar == key; +- } +- +- Foo*& GetLink(Foo* value) const +- { +- return value->fNext; +- } +- }; +-*/ +- +- +-struct MallocAllocator +-{ +- void* Allocate(size_t size) const +- { +- return malloc(size); +- } +- +- void Free(void* memory) const +- { +- free(memory); +- } +-}; +- +- +-template +-class BOpenHashTable +-{ +-public: +- typedef BOpenHashTable HashTable; +- typedef typename Definition::KeyType KeyType; +- typedef typename Definition::ValueType ValueType; +- +- static const size_t kMinimumSize = 8; +- +- // All allocations are of power of 2 lengths. +- +- // regrowth factor: 200 / 256 = 78.125% +- // 50 / 256 = 19.53125% +- +- BOpenHashTable() +- : +- fTableSize(0), +- fItemCount(0), +- fTable(NULL) +- { +- } +- +- BOpenHashTable(const Definition& definition) +- : +- fDefinition(definition), +- fTableSize(0), +- fItemCount(0), +- fTable(NULL) +- { +- } +- +- BOpenHashTable(const Definition& definition, const Allocator& allocator) +- : +- fDefinition(definition), +- fAllocator(allocator), +- fTableSize(0), +- fItemCount(0), +- fTable(NULL) +- { +- } +- +- ~BOpenHashTable() +- { +- fAllocator.Free(fTable); +- } +- +- status_t Init(size_t initialSize = kMinimumSize) +- { +- if (initialSize > 0 && !_Resize(initialSize)) +- return B_NO_MEMORY; +- return B_OK; +- } +- +- size_t TableSize() const +- { +- return fTableSize; +- } +- +- size_t CountElements() const +- { +- return fItemCount; +- } +- +- ValueType* Lookup(const KeyType& key) const +- { +- if (fTableSize == 0) +- return NULL; +- +- size_t index = fDefinition.HashKey(key) & (fTableSize - 1); +- ValueType* slot = fTable[index]; +- +- while (slot) +- { +- if (fDefinition.Compare(key, slot)) +- break; +- slot = _Link(slot); +- } +- +- return slot; +- } +- +- status_t Insert(ValueType* value) +- { +- if (fTableSize == 0) +- { +- if (!_Resize(kMinimumSize)) +- return B_NO_MEMORY; +- } +- else if (AutoExpand && fItemCount >= (fTableSize * 200 / 256)) +- _Resize(fTableSize * 2); +- +- InsertUnchecked(value); +- return B_OK; +- } +- +- void InsertUnchecked(ValueType* value) +- { +- if (CheckDuplicates && _ExhaustiveSearch(value)) +- { +-#ifdef _KERNEL_MODE +- panic("Hash Table: value already in table."); +-#else +- debugger("Hash Table: value already in table."); +-#endif +- } +- +- _Insert(fTable, fTableSize, value); +- fItemCount++; +- } +- +- // TODO: a ValueType* Remove(const KeyType& key) method is missing +- +- bool Remove(ValueType* value) +- { +- if (!RemoveUnchecked(value)) +- return false; +- +- if (AutoExpand && fTableSize > kMinimumSize +- && fItemCount < (fTableSize * 50 / 256)) +- _Resize(fTableSize / 2); +- +- return true; +- } +- +- bool RemoveUnchecked(ValueType* value) +- { +- size_t index = fDefinition.Hash(value) & (fTableSize - 1); +- ValueType* previous = NULL; +- ValueType* slot = fTable[index]; +- +- while (slot) +- { +- ValueType* next = _Link(slot); +- +- if (value == slot) +- { +- if (previous) +- _Link(previous) = next; +- else +- fTable[index] = next; +- break; +- } +- +- previous = slot; +- slot = next; +- } +- +- if (slot == NULL) +- return false; +- +- if (CheckDuplicates && _ExhaustiveSearch(value)) +- { +-#ifdef _KERNEL_MODE +- panic("Hash Table: duplicate detected."); +-#else +- debugger("Hash Table: duplicate detected."); +-#endif +- } +- +- fItemCount--; +- return true; +- } +- +- /*! Removes all elements from the hash table. No resizing happens. The +- elements are not deleted. If \a returnElements is \c true, the method +- returns all elements chained via their hash table link. +- */ +- ValueType* Clear(bool returnElements = false) +- { +- if (this->fItemCount == 0) +- return NULL; +- +- ValueType* result = NULL; +- +- if (returnElements) +- { +- ValueType** nextPointer = &result; +- +- // iterate through all buckets +- for (size_t i = 0; i < fTableSize; i++) +- { +- ValueType* element = fTable[i]; +- if (element != NULL) +- { +- // add the bucket to the list +- *nextPointer = element; +- +- // update nextPointer to point to the fNext of the last +- // element in the bucket +- while (element != NULL) +- { +- nextPointer = &_Link(element); +- element = *nextPointer; +- } +- } +- } +- } +- +- memset(this->fTable, 0, sizeof(ValueType*) * this->fTableSize); +- +- return result; +- } +- +- /*! If the table needs resizing, the number of bytes for the required +- allocation is returned. If no resizing is needed, 0 is returned. +- */ +- size_t ResizeNeeded() const +- { +- size_t size = fTableSize; +- if (size == 0 || fItemCount >= (size * 200 / 256)) +- { +- // grow table +- if (size == 0) +- size = kMinimumSize; +- while (fItemCount >= size * 200 / 256) +- size <<= 1; +- } +- else if (size > kMinimumSize && fItemCount < size * 50 / 256) +- { +- // shrink table +- while (fItemCount < size * 50 / 256) +- size >>= 1; +- if (size < kMinimumSize) +- size = kMinimumSize; +- } +- +- if (size == fTableSize) +- return 0; +- +- return size * sizeof(ValueType*); +- } +- +- /*! Resizes the table using the given allocation. The allocation must not +- be \c NULL. It must be of size \a size, which must a value returned +- earlier by ResizeNeeded(). If the size requirements have changed in the +- meantime, the method free()s the given allocation and returns \c false, +- unless \a force is \c true, in which case the supplied allocation is +- used in any event. +- Otherwise \c true is returned. +- If \a oldTable is non-null and resizing is successful, the old table +- will not be freed, but will be returned via this parameter instead. +- */ +- bool Resize(void* allocation, size_t size, bool force = false, +- void** oldTable = NULL) +- { +- if (!force && size != ResizeNeeded()) +- { +- fAllocator.Free(allocation); +- return false; +- } +- +- _Resize((ValueType**)allocation, size / sizeof(ValueType*), oldTable); +- return true; +- } +- +- class Iterator +- { +- public: +- Iterator(const HashTable* table) +- : fTable(table) +- { +- Rewind(); +- } +- +- Iterator(const HashTable* table, size_t index, ValueType* value) +- : fTable(table), fIndex(index), fNext(value) {} +- +- bool HasNext() const { return fNext != NULL; } +- +- ValueType* Next() +- { +- ValueType* current = fNext; +- _GetNext(); +- return current; +- } +- +- void Rewind() +- { +- // get the first one +- fIndex = 0; +- fNext = NULL; +- _GetNext(); +- } +- +- protected: +- Iterator() {} +- +- void _GetNext() +- { +- if (fNext) +- fNext = fTable->_Link(fNext); +- +- while (fNext == NULL && fIndex < fTable->fTableSize) +- fNext = fTable->fTable[fIndex++]; +- } +- +- const HashTable* fTable; +- size_t fIndex; +- ValueType* fNext; +- }; +- +- Iterator GetIterator() const +- { +- return Iterator(this); +- } +- +- Iterator GetIterator(const KeyType& key) const +- { +- if (fTableSize == 0) +- return Iterator(this, fTableSize, NULL); +- +- size_t index = fDefinition.HashKey(key) & (fTableSize - 1); +- ValueType* slot = fTable[index]; +- +- while (slot) +- { +- if (fDefinition.Compare(key, slot)) +- break; +- slot = _Link(slot); +- } +- +- if (slot == NULL) +- return Iterator(this, fTableSize, NULL); +- +- return Iterator(this, index + 1, slot); +- } +- +-protected: +- // for g++ 2.95 +- friend class Iterator; +- +- void _Insert(ValueType** table, size_t tableSize, ValueType* value) +- { +- size_t index = fDefinition.Hash(value) & (tableSize - 1); +- +- _Link(value) = table[index]; +- table[index] = value; +- } +- +- bool _Resize(size_t newSize) +- { +- ValueType** newTable +- = (ValueType**)fAllocator.Allocate(sizeof(ValueType*) * newSize); +- if (newTable == NULL) +- return false; +- +- _Resize(newTable, newSize); +- return true; +- } +- +- void _Resize(ValueType** newTable, size_t newSize, void** _oldTable = NULL) +- { +- for (size_t i = 0; i < newSize; i++) +- newTable[i] = NULL; +- +- if (fTable) +- { +- for (size_t i = 0; i < fTableSize; i++) +- { +- ValueType* bucket = fTable[i]; +- while (bucket) +- { +- ValueType* next = _Link(bucket); +- _Insert(newTable, newSize, bucket); +- bucket = next; +- } +- } +- +- if (_oldTable != NULL) +- *_oldTable = fTable; +- else +- fAllocator.Free(fTable); +- } +- else if (_oldTable != NULL) +- *_oldTable = NULL; +- +- fTableSize = newSize; +- fTable = newTable; +- } +- +- ValueType*& _Link(ValueType* bucket) const +- { +- return fDefinition.GetLink(bucket); +- } +- +- bool _ExhaustiveSearch(ValueType* value) const +- { +- for (size_t i = 0; i < fTableSize; i++) +- { +- ValueType* bucket = fTable[i]; +- while (bucket) { +- if (bucket == value) +- return true; +- bucket = _Link(bucket); +- } +- } +- +- return false; +- } +- +- Definition fDefinition; +- Allocator fAllocator; +- size_t fTableSize; +- size_t fItemCount; +- ValueType** fTable; +-}; +- +-#endif /* !GA_INCLUDED_SRC_haiku_SharedFolders_OpenHashTable_h */ +- +diff --git a/src/VBox/Additions/haiku/SharedFolders/lock.h b/src/VBox/Additions/haiku/SharedFolders/lock.h +index dc65b80..a3df675 100644 +--- a/src/VBox/Additions/haiku/SharedFolders/lock.h ++++ b/src/VBox/Additions/haiku/SharedFolders/lock.h +@@ -67,7 +67,7 @@ typedef struct rw_lock { + const char* name; + struct rw_lock_waiter* waiters; + thread_id holder; +- vint32 count; ++ int32 count; + int32 owner_count; + int16 active_readers; + // Only > 0 while a writer is waiting: number +diff --git a/src/VBox/Additions/haiku/SharedFolders/vboxsf.c b/src/VBox/Additions/haiku/SharedFolders/vboxsf.c +index 5e2b88c..ac44ffa 100644 +--- a/src/VBox/Additions/haiku/SharedFolders/vboxsf.c ++++ b/src/VBox/Additions/haiku/SharedFolders/vboxsf.c +@@ -44,6 +44,8 @@ + */ + + #include "vboxsf.h" ++#include ++#include + + #define MODULE_NAME "file_systems/vboxsf" + #define FS_NAME "vboxsf" +@@ -51,7 +53,7 @@ + + VBGLSFCLIENT g_clientHandle; + static fs_volume_ops vboxsf_volume_ops; +-static fs_vnode_ops vboxsf_vnode_ops; ++static vboxsf_vnode * head = NULL; + + status_t init_module(void) + { +@@ -97,7 +99,13 @@ status_t init_module(void) + dprintf("get_module(%s) failed\n", VBOXGUEST_MODULE_NAME); + return B_ERROR; + } +- ++ ++ if (RT_FAILURE(RTR0Init(0))) ++ { ++ dprintf("RTR0Init failed\n"); ++ return B_ERROR; ++ ++ } + if (RT_FAILURE(VbglR0SfInit())) + { + dprintf("VbglR0SfInit failed\n"); +@@ -194,7 +202,6 @@ PSHFLSTRING concat_cstr_shflstring(const char* const s1, PSHFLSTRING s2) + + PSHFLSTRING build_path(vboxsf_vnode* dir, const char* const name) + { +- dprintf("*** build_path(%p, %p)\n", dir, name); + if (!dir || !name) + return NULL; + +@@ -208,6 +215,7 @@ PSHFLSTRING build_path(vboxsf_vnode* dir, const char* const name) + rv->u16Length = len; + rv->u16Size = rv->u16Length + 1; + } ++ + return rv; + } + +@@ -231,7 +239,7 @@ status_t mount(fs_volume *volume, const char *device, uint32 flags, const char * + + if (rv == 0) + { +- vboxsf_vnode* root_vnode; ++ vboxsf_vnode* root_vnode; + + PSHFLSTRING name = make_shflstring(""); + if (!name) +@@ -239,8 +247,8 @@ status_t mount(fs_volume *volume, const char *device, uint32 flags, const char * + dprintf(FS_NAME ": make_shflstring() failed\n"); + return B_NO_MEMORY; + } +- +- status_t rs = vboxsf_new_vnode(&vbsfvolume->map, name, name, &root_vnode); ++ status_t rs = vboxsf_new_vnode(volume, &vbsfvolume->map, name, name, 1, S_IFDIR | S_IRUSR | S_IROTH | S_IWUSR | S_IRGRP | S_IWGRP | S_IWOTH | S_IXUSR | S_IXGRP | S_IXOTH, &root_vnode, true); ++ head = root_vnode; + dprintf(FS_NAME ": allocated %p (path=%p name=%p)\n", root_vnode, root_vnode->path, root_vnode->name); + + if (rs != B_OK) +@@ -249,7 +257,7 @@ status_t mount(fs_volume *volume, const char *device, uint32 flags, const char * + return rs; + } + +- rs = publish_vnode(volume, root_vnode->vnode, root_vnode, &vboxsf_vnode_ops, S_IFDIR, 0); ++ rs = publish_vnode(volume, root_vnode->vnode, root_vnode, &vboxsf_vnode_ops, S_IFDIR | S_IRUSR | S_IROTH | S_IWUSR | S_IRGRP | S_IWGRP | S_IWOTH | S_IXUSR | S_IXGRP | S_IXOTH, 0); + dprintf(FS_NAME ": publish_vnode(): %d\n", (int)rs); + *_rootVnodeID = root_vnode->vnode; + volume->ops = &vboxsf_volume_ops; +@@ -313,7 +321,9 @@ status_t vboxsf_read_stat(fs_volume* _volume, fs_vnode* _vnode, struct stat* st) + st->st_blocks = params.Info.cbAllocated; + st->st_atime = RTTimeSpecGetSeconds(¶ms.Info.AccessTime); + st->st_mtime = RTTimeSpecGetSeconds(¶ms.Info.ModificationTime); +- st->st_ctime = RTTimeSpecGetSeconds(¶ms.Info.BirthTime); ++ st->st_ctime = RTTimeSpecGetSeconds(¶ms.Info.ChangeTime); ++ dprintf("sf_stat: returning B_OK\n"); ++ + return B_OK; + } + +@@ -323,9 +333,11 @@ status_t vboxsf_open_dir(fs_volume* _volume, fs_vnode* _vnode, void** _cookie) + vboxsf_volume* volume = _volume->private_volume; + vboxsf_vnode* vnode = _vnode->private_node; + SHFLCREATEPARMS params; ++ dprintf(FS_NAME ": vboxsf_open_dir %s\n", vnode->path->String.utf8); + + RT_ZERO(params); + params.Handle = SHFL_HANDLE_NIL; ++ params.Info.cbObject = 0; + params.CreateFlags = SHFL_CF_DIRECTORY | SHFL_CF_ACT_OPEN_IF_EXISTS | SHFL_CF_ACT_FAIL_IF_NEW | SHFL_CF_ACCESS_READ; + + int rc = VbglR0SfCreate(&g_clientHandle, &volume->map, vnode->path, ¶ms); +@@ -341,10 +353,14 @@ status_t vboxsf_open_dir(fs_volume* _volume, fs_vnode* _vnode, void** _cookie) + cookie->has_more_files = true; + cookie->buffer_start = cookie->buffer = NULL; + cookie->buffer_length = cookie->num_files = 0; ++ dprintf(FS_NAME ": vboxsf_open_dir ret OK\n"); + return B_OK; + } +- else ++ else { ++ dprintf(FS_NAME ": vboxsf_open_dir ret ENTRY NOT FOUND\n"); ++ + return B_ENTRY_NOT_FOUND; ++ } + } + else + { +@@ -353,11 +369,47 @@ status_t vboxsf_open_dir(fs_volume* _volume, fs_vnode* _vnode, void** _cookie) + } + } + ++bool find_node_ancestor_by_ref(ino_t ref, vboxsf_vnode ** outNode) ++{ ++ bool found = false; ++ vboxsf_vnode * new_vnode = head; ++ while (new_vnode != NULL) ++ { ++ if (new_vnode->int_next->vnode == ref) ++ { ++ found = true; ++ *outNode = new_vnode; ++ break; ++ } ++ new_vnode = new_vnode->int_next; ++ } ++ return found; ++} ++ ++bool find_node_by_name(const char * path, vboxsf_vnode ** outNode) ++{ ++ bool found = false; ++ vboxsf_vnode * new_vnode = head; ++ while (new_vnode != NULL) ++ { ++ dprintf("find_node_by_name %s == %s\n", path, new_vnode->path->String.utf8); ++ if (strcmp(new_vnode->path->String.utf8,path) == 0) ++ { ++ found = true; ++ *outNode = new_vnode; ++ break; ++ } ++ new_vnode = new_vnode->int_next; ++ } ++ return found; ++} + + /** read a single entry from a dir */ +-status_t vboxsf_read_dir_1(vboxsf_volume* volume, vboxsf_vnode* vnode, vboxsf_dir_cookie* cookie, ++status_t vboxsf_read_dir_1(fs_volume* _volume, vboxsf_volume* volume, vboxsf_vnode* vnode, vboxsf_dir_cookie* cookie, + struct dirent* buffer, size_t bufferSize) + { ++ dprintf(FS_NAME ": vboxsf_read_dir_1\n"); ++ + dprintf("%p, %d, %p\n", cookie, cookie->has_more_files, cookie->buffer); + if (!cookie->has_more_files) + return B_ENTRY_NOT_FOUND; +@@ -399,22 +451,42 @@ status_t vboxsf_read_dir_1(vboxsf_volume* volume, vboxsf_vnode* vnode, vboxsf_di + dprintf(FS_NAME ": make_shflstring() failed\n"); + return B_NO_MEMORY; + } +- +- vboxsf_vnode* new_vnode; +- int rv = vboxsf_new_vnode(&volume->map, build_path(vnode, name1->String.utf8), name1, &new_vnode); +- if (rv != B_OK) +- { +- dprintf(FS_NAME ": vboxsf_new_vnode() failed\n"); +- return rv; +- } +- ++ dprintf(FS_NAME ": vboxsf_read_dir_1 found: %s\n", name1->String.utf8); ++ ++ ino_t entry; ++ ++ if (strcmp(name1->String.utf8,".")==0) ++ { ++ //vnodeid is this dir ++ entry = vnode->vnode; ++ } ++ else if (strcmp(name1->String.utf8,"..")==0) ++ { ++ //vnodeid is parent of this dir ++ entry = vnode->parentvnode; ++ } else ++ { ++ //create a new node for an actual entry ++ vboxsf_vnode* new_vnode; ++ PSHFLSTRING path = build_path(vnode, name1->String.utf8); ++ if (!find_node_by_name(path->String.utf8, &new_vnode)) ++ { ++ int rv = vboxsf_new_vnode(_volume, &volume->map, path, name1, vnode->vnode, mode_from_fmode(cookie->buffer->Info.Attr.fMode), &new_vnode, false); ++ if (rv != B_OK) ++ { ++ dprintf(FS_NAME ": vboxsf_new_vnode() failed\n"); ++ free(path); ++ return rv; ++ } ++ } ++ entry = new_vnode->vnode; ++ } + buffer->d_dev = 0; + buffer->d_pdev = 0; +- buffer->d_ino = new_vnode->vnode; ++ buffer->d_ino = entry; + buffer->d_pino = vnode->vnode; + buffer->d_reclen = sizeof(struct dirent) + cookie->buffer->name.u16Length; + strncpy(buffer->d_name, cookie->buffer->name.String.utf8, NAME_MAX); +- + size_t size = offsetof(SHFLDIRINFO, name.String) + cookie->buffer->name.u16Size; + cookie->buffer = ((void*)cookie->buffer + size); + cookie->index++; +@@ -438,9 +510,11 @@ status_t vboxsf_read_dir(fs_volume* _volume, fs_vnode* _vnode, void* _cookie, + uint32 num_read = 0; + status_t rv = B_OK; + ++ dprintf(FS_NAME ": vboxsf_read_dir\n"); ++ + for (num_read = 0; num_read < *_num && cookie->has_more_files; num_read++) + { +- rv = vboxsf_read_dir_1(volume, vnode, cookie, buffer, bufferSize); ++ rv = vboxsf_read_dir_1(_volume, volume, vnode, cookie, buffer, bufferSize); + if (rv == B_BUFFER_OVERFLOW || rv == B_ENTRY_NOT_FOUND) + { + // hit end of at least one of the buffers - not really an error +@@ -471,6 +545,8 @@ status_t vboxsf_free_dir_cookie(fs_volume* _volume, fs_vnode* vnode, void* _cook + + status_t vboxsf_read_fs_info(fs_volume* _volume, struct fs_info* info) + { ++ dprintf(FS_NAME ": vboxsf_read_fs_info\n"); ++ + vboxsf_volume* volume = _volume->private_volume; + + SHFLVOLINFO volume_info; +@@ -484,7 +560,7 @@ status_t vboxsf_read_fs_info(fs_volume* _volume, struct fs_info* info) + return vbox_err_to_haiku_err(rc); + } + +- info->flags = B_FS_IS_PERSISTENT; ++ info->flags = B_FS_IS_PERSISTENT | B_FS_SUPPORTS_NODE_MONITORING; + if (volume_info.fsProperties.fReadOnly) + info->flags |= B_FS_IS_READONLY; + +@@ -500,11 +576,37 @@ status_t vboxsf_read_fs_info(fs_volume* _volume, struct fs_info* info) + return B_OK; + } + ++status_t vboxsf_access(fs_volume* volume, fs_vnode* vnode, int mode) ++{ ++ vboxsf_vnode* node = vnode->private_node; ++ ++ mode_t attributes = node->mode; ++ ++ if (((mode & R_OK) == R_OK && !(((attributes & S_IRUSR) == S_IRUSR) || ((attributes & S_IRGRP) == S_IRGRP))) ++ || ((mode & W_OK) == W_OK && !(((attributes & S_IWUSR) == S_IWUSR) || ((attributes & S_IWGRP) == S_IWGRP))) ++ || ((mode & X_OK) == X_OK && !(((attributes & S_IXUSR) == S_IXUSR) || ((attributes & S_IXGRP) == S_IXGRP)))) ++ return B_PERMISSION_DENIED; ++ ++ return B_OK; ++} + + status_t vboxsf_lookup(fs_volume* _volume, fs_vnode* dir, const char* name, ino_t* _id) + { + dprintf(FS_NAME ": lookup %s\n", name); + vboxsf_volume* volume = _volume->private_volume; ++ vboxsf_vnode* sfnode = dir->private_node; ++ ++ if (strcmp(name,".")==0) { ++ //return dir node ++ *_id = sfnode->vnode; ++ return get_vnode(_volume, *_id, NULL); ++ } ++ if (strcmp(name,"..")==0) { ++ //return parent node ++ *_id = sfnode->parentvnode; ++ return get_vnode(_volume, *_id, NULL); ++ } ++ + SHFLCREATEPARMS params; + + RT_ZERO(params); +@@ -517,23 +619,31 @@ status_t vboxsf_lookup(fs_volume* _volume, fs_vnode* dir, const char* name, ino_ + dprintf(FS_NAME ": make_shflstring() failed\n"); + return B_NO_MEMORY; + } ++ ++ dprintf(FS_NAME ": lookup full path %s\n", path->String.utf8); ++ vboxsf_vnode* vn; ++ if (find_node_by_name(path->String.utf8, &vn)) ++ { ++ *_id = vn->vnode; ++ dprintf(FS_NAME ": attempt to return pointer to inode %ld\n", vn->vnode); ++ return get_vnode(_volume, *_id, NULL); ++ } + + int rc = VbglR0SfCreate(&g_clientHandle, &volume->map, path, ¶ms); + if (RT_SUCCESS(rc)) + { + if (params.Result == SHFL_FILE_EXISTS) + { +- vboxsf_vnode* vn; +- status_t rv = vboxsf_new_vnode(&volume->map, path, path, &vn); +- if (rv == B_OK) +- { +- *_id = vn->vnode; +- rv = publish_vnode(_volume, vn->vnode, vn, &vboxsf_vnode_ops, mode_from_fmode(params.Info.Attr.fMode), 0); +- } +- return rv; ++ dprintf(FS_NAME ": no existing node\n"); ++ status_t rv = vboxsf_new_vnode(_volume, &volume->map, path, path, sfnode->vnode, mode_from_fmode(params.Info.Attr.fMode), &vn, false); ++ *_id = vn->vnode; ++ ++ dprintf(FS_NAME ": attempt to return pointer to inode %ld\n", vn->vnode); ++ return get_vnode(_volume, *_id, NULL); + } + else + { ++ dprintf(FS_NAME ": for %s return path not found\n", name); + free(path); + return B_ENTRY_NOT_FOUND; + } +@@ -606,7 +716,8 @@ status_t vboxsf_open(fs_volume* _volume, fs_vnode* _vnode, int openMode, void** + + RT_ZERO(params); + params.Handle = SHFL_HANDLE_NIL; +- ++ params.Info.cbObject = 0; ++ + if (openMode & O_RDWR) + params.CreateFlags |= SHFL_CF_ACCESS_READWRITE; + else if (openMode & O_RDONLY) +@@ -662,6 +773,7 @@ status_t vboxsf_open(fs_volume* _volume, fs_vnode* _vnode, int openMode, void** + status_t vboxsf_create(fs_volume* _volume, fs_vnode* _dir, const char *name, int openMode, int perms, void **_cookie, ino_t *_newVnodeID) + { + vboxsf_volume* volume = _volume->private_volume; ++ vboxsf_vnode* sfnode = _dir->private_node; + + SHFLCREATEPARMS params; + +@@ -719,7 +831,13 @@ status_t vboxsf_create(fs_volume* _volume, fs_vnode* _dir, const char *name, int + cookie->path = path; + + *_cookie = cookie; +- return vboxsf_lookup(_volume, _dir, name, _newVnodeID); ++ ++ vboxsf_vnode* vn; ++ status_t rv = vboxsf_new_vnode(_volume, &volume->map, path, path, sfnode->vnode, mode_from_fmode(params.Info.Attr.fMode), &vn, false); ++ *_newVnodeID = vn->vnode; ++ get_vnode(_volume, vn->vnode, NULL); ++ get_vnode(_volume, vn->vnode, NULL); ++ return notify_entry_created(volume->rootid, sfnode->vnode, path->String.utf8, vn->vnode); + } + + +@@ -742,9 +860,14 @@ status_t vboxsf_rewind_dir(fs_volume* _volume, fs_vnode* _vnode, void* _cookie) + } + + +-status_t vboxsf_close_dir(fs_volume *volume, fs_vnode *vnode, void *cookie) ++status_t vboxsf_close_dir(fs_volume *_volume, fs_vnode *vnode, void * _cookie) + { +- return B_OK; ++ vboxsf_volume* volume = _volume->private_volume; ++ vboxsf_file_cookie* cookie = _cookie; ++ ++ int rc = VbglR0SfClose(&g_clientHandle, &volume->map, cookie->handle); ++ dprintf("VbglR0SfClose dir returned %d\n", rc); ++ return vbox_err_to_haiku_err(rc); + } + + +@@ -808,20 +931,33 @@ status_t vboxsf_create_dir(fs_volume *_volume, fs_vnode *parent, const char *nam + vboxsf_volume* volume = _volume->private_volume; + + SHFLCREATEPARMS params; +- params.Handle = 0; ++ params.Handle = SHFL_HANDLE_NIL; + params.Info.cbObject = 0; + params.CreateFlags = SHFL_CF_DIRECTORY | SHFL_CF_ACT_CREATE_IF_NEW | +- SHFL_CF_ACT_FAIL_IF_EXISTS | SHFL_CF_ACCESS_READ; ++ SHFL_CF_ACT_FAIL_IF_EXISTS | SHFL_CF_ACCESS_READWRITE; + + PSHFLSTRING path = build_path(parent->private_node, name); + int rc = VbglR0SfCreate(&g_clientHandle, &volume->map, path, ¶ms); +- free(path); +- /** @todo r=ramshankar: we should perhaps also check rc here and change +- * Handle initialization from 0 to SHFL_HANDLE_NIL. */ ++ ++ dprintf("vboxsf_create_dir path %s\n", path->String.utf8); ++ ++ if (RT_FAILURE(rc)) ++ { ++ free(path); ++ return (vbox_err_to_haiku_err(rc)); ++ } + if (params.Handle == SHFL_HANDLE_NIL) ++ { ++ free(path); + return vbox_err_to_haiku_err(rc); ++ } ++ ++ vboxsf_vnode* dir_vnode; ++ vboxsf_vnode* parentnode = parent->private_node; ++ ++ status_t rs = vboxsf_new_vnode(_volume, &volume->map, path, path, parentnode->vnode, mode_from_fmode(params.Info.Attr.fMode), &dir_vnode, false); + VbglR0SfClose(&g_clientHandle, &volume->map, params.Handle); +- return B_OK; ++ return notify_entry_created(volume->rootid, parentnode->vnode, dir_vnode->path->String.utf8, dir_vnode->vnode); + } + + +@@ -830,19 +966,56 @@ status_t vboxsf_remove_dir(fs_volume *_volume, fs_vnode *parent, const char *nam + vboxsf_volume* volume = _volume->private_volume; + + PSHFLSTRING path = build_path(parent->private_node, name); ++ dprintf("vboxsf_remove_dir path %s\n", path->String.utf8); ++ ++ vboxsf_vnode* new_vnode; ++ ++ if (!find_node_by_name(path->String.utf8, &new_vnode)) ++ { ++ free(path); ++ return B_ENTRY_NOT_FOUND; ++ } + int rc = VbglR0SfRemove(&g_clientHandle, &volume->map, path, SHFL_REMOVE_DIR); ++ if (RT_SUCCESS(rc)) { ++ remove_vnode(_volume, new_vnode->vnode); ++ put_vnode(_volume, new_vnode->vnode); ++ } + free(path); +- ++ dprintf("vboxsf_remove_dir returned %d\n", rc); ++ + return vbox_err_to_haiku_err(rc); + } + + + status_t vboxsf_unlink(fs_volume *_volume, fs_vnode *parent, const char *name) + { ++ dprintf("vboxsf_unlink file %s\n", name); + vboxsf_volume* volume = _volume->private_volume; + + PSHFLSTRING path = build_path(parent->private_node, name); ++ ++ vboxsf_vnode* new_vnode; ++ vboxsf_vnode* oldnode; ++ if (!find_node_by_name(path->String.utf8, &new_vnode)) ++ { ++ free(path); ++ return B_ENTRY_NOT_FOUND; ++ } ++ get_vnode(_volume, new_vnode->vnode, (void**)&oldnode); ++ + int rc = VbglR0SfRemove(&g_clientHandle, &volume->map, path, SHFL_REMOVE_FILE); ++ if (RT_SUCCESS(rc)) ++ { ++ ino_t entry = new_vnode->vnode; ++ vboxsf_vnode* parentnode = parent->private_node; ++ remove_vnode(_volume, new_vnode->vnode); ++ status_t status = notify_entry_removed(volume->rootid, parentnode->vnode, name, new_vnode->vnode); ++ put_vnode(_volume, new_vnode->vnode); ++ //put_vnode(_volume, new_vnode->vnode); ++ free(path); ++ return status; ++ } ++ put_vnode(_volume, new_vnode->vnode); + free(path); + + return vbox_err_to_haiku_err(rc); +@@ -857,10 +1030,39 @@ status_t vboxsf_link(fs_volume *volume, fs_vnode *dir, const char *name, fs_vnod + status_t vboxsf_rename(fs_volume* _volume, fs_vnode* fromDir, const char* fromName, fs_vnode* toDir, const char* toName) + { + vboxsf_volume* volume = _volume->private_volume; +- +- PSHFLSTRING oldpath = build_path(fromDir->private_node, fromName); +- PSHFLSTRING newpath = build_path(toDir->private_node, toName); +- int rc = VbglR0SfRename(&g_clientHandle, &volume->map, oldpath, newpath, SHFL_RENAME_FILE | SHFL_RENAME_REPLACE_IF_EXISTS); ++ vboxsf_vnode * fromnode = fromDir->private_node; ++ vboxsf_vnode * tonode = toDir->private_node; ++ ++ dprintf("vboxsf_rename called fromName:%s toName:%s\n", fromName, toName); ++ PSHFLSTRING oldpath = build_path(fromnode, fromName); ++ PSHFLSTRING newpath = build_path(tonode, toName); ++ ++ vboxsf_vnode * vn; ++ if (!find_node_by_name(oldpath->String.utf8, &vn)) ++ { ++ free(oldpath); ++ free(newpath); ++ } ++ mode_t mode = S_IRUSR | S_IROTH | S_IWUSR | S_IRGRP | S_IWGRP | S_IWOTH | S_IXUSR | S_IXGRP | S_IXOTH; ++ bool isDir = (vn->mode & S_IFDIR) == S_IFDIR; ++ int rc = VbglR0SfRename(&g_clientHandle, &volume->map, oldpath, newpath, isDir ? SHFL_RENAME_DIR : SHFL_RENAME_FILE | SHFL_RENAME_REPLACE_IF_EXISTS); ++ dprintf("vboxsf_rename returned %d\n", rc); ++ if (RT_SUCCESS(rc)) ++ { ++ get_vnode(_volume, vn->vnode, (void**)&vn); ++ //replace old entry values ++ free(vn->path); ++ vn->path = newpath; ++ vn->parentvnode = tonode->vnode; ++ //create new entry ++ dprintf(FS_NAME ": attempt to return pointer to inode %ld\n", vn->vnode); ++ put_vnode(_volume, vn->vnode); ++ notify_entry_moved(volume->rootid, fromnode->vnode, fromName, tonode->vnode, toName, vn->vnode); ++ ++ free(oldpath); ++ return B_OK; ++ } ++ + free(oldpath); + free(newpath); + +@@ -906,8 +1108,10 @@ status_t vbox_err_to_haiku_err(int rc) + case VINF_SUCCESS: return B_OK; + case VERR_INVALID_POINTER: return B_BAD_ADDRESS; + case VERR_INVALID_PARAMETER: return B_BAD_VALUE; ++ case VERR_ACCESS_DENIED: return B_PERMISSION_DENIED; + case VERR_PERMISSION_DENIED: return B_PERMISSION_DENIED; + case VERR_NOT_IMPLEMENTED: return B_UNSUPPORTED; ++ case VERR_INVALID_NAME: return B_ENTRY_NOT_FOUND; + case VERR_FILE_NOT_FOUND: return B_ENTRY_NOT_FOUND; + + case SHFL_PATH_NOT_FOUND: +@@ -939,11 +1143,11 @@ static status_t std_ops(int32 op, ...) + + static fs_volume_ops vboxsf_volume_ops = + { +- unmount, +- vboxsf_read_fs_info, ++ &unmount, ++ &vboxsf_read_fs_info, + NULL, /* write_fs_info */ + NULL, /* sync */ +- vboxsf_get_vnode, ++ &vboxsf_get_vnode, + NULL, /* open_index_dir */ + NULL, /* close_index_dir */ + NULL, /* free_index_dir_cookie */ +@@ -962,12 +1166,12 @@ static fs_volume_ops vboxsf_volume_ops = + NULL, /* delete_sub_vnode */ + }; + +-static fs_vnode_ops vboxsf_vnode_ops = ++fs_vnode_ops vboxsf_vnode_ops = + { +- vboxsf_lookup, ++ &vboxsf_lookup, + NULL, /* get_vnode_name */ +- vboxsf_put_vnode, +- NULL, /* remove_vnode */ ++ &vboxsf_put_vnode, ++ &vboxsf_remove_vnode, /* remove_vnode */ + NULL, /* can_page */ + NULL, /* read_pages */ + NULL, /* write_pages */ +@@ -979,28 +1183,28 @@ static fs_vnode_ops vboxsf_vnode_ops = + NULL, /* select */ + NULL, /* deselect */ + NULL, /* fsync */ +- vboxsf_read_symlink, +- vboxsf_create_symlink, +- vboxsf_link, +- vboxsf_unlink, +- vboxsf_rename, +- NULL, /* access */ +- vboxsf_read_stat, +- vboxsf_write_stat, ++ &vboxsf_read_symlink, ++ &vboxsf_create_symlink, ++ &vboxsf_link, ++ &vboxsf_unlink, ++ &vboxsf_rename, ++ &vboxsf_access, /* access */ ++ &vboxsf_read_stat, ++ &vboxsf_write_stat, + NULL, /* preallocate */ +- vboxsf_create, +- vboxsf_open, +- vboxsf_close, +- vboxsf_free_cookie, +- vboxsf_read, +- vboxsf_write, +- vboxsf_create_dir, +- vboxsf_remove_dir, +- vboxsf_open_dir, +- vboxsf_close_dir, +- vboxsf_free_dir_cookie, +- vboxsf_read_dir, +- vboxsf_rewind_dir, ++ &vboxsf_create, ++ &vboxsf_open, ++ &vboxsf_close, ++ &vboxsf_free_cookie, ++ &vboxsf_read, ++ &vboxsf_write, ++ &vboxsf_create_dir, ++ &vboxsf_remove_dir, ++ &vboxsf_open_dir, ++ &vboxsf_close_dir, ++ &vboxsf_free_dir_cookie, ++ &vboxsf_read_dir, ++ &vboxsf_rewind_dir, + NULL, /* open_attr_dir */ + NULL, /* close_attr_dir */ + NULL, /* free_attr_dir_cookie */ +@@ -1034,7 +1238,7 @@ static file_system_module_info sVBoxSharedFileSystem = + NULL, /* scan_partition */ + NULL, /* free_identify_partition_cookie */ + NULL, /* free_partition_content_cookie */ +- mount, ++ &mount, + }; + + module_info *modules[] = +diff --git a/src/VBox/Additions/haiku/SharedFolders/vboxsf.h b/src/VBox/Additions/haiku/SharedFolders/vboxsf.h +index a4aa8f5..b53fd48 100644 +--- a/src/VBox/Additions/haiku/SharedFolders/vboxsf.h ++++ b/src/VBox/Additions/haiku/SharedFolders/vboxsf.h +@@ -71,7 +71,10 @@ typedef struct vboxsf_vnode + PSHFLSTRING name; + PSHFLSTRING path; + ino_t vnode; ++ mode_t mode; ++ ino_t parentvnode; + struct vboxsf_vnode* next; ++ struct vboxsf_vnode* int_next; + } vboxsf_vnode; + + typedef struct vboxsf_dir_cookie +@@ -94,17 +97,24 @@ typedef struct vboxsf_file_cookie + extern "C" { + #endif + +-status_t vboxsf_new_vnode(PVBGLSFMAP map, PSHFLSTRING path, PSHFLSTRING name, vboxsf_vnode** p); ++bool find_node_ancestor_by_ref(ino_t ref, vboxsf_vnode ** outNode); ++ ++status_t vboxsf_new_vnode(fs_volume* volume, PVBGLSFMAP map, PSHFLSTRING path, PSHFLSTRING name, ino_t parent, mode_t mode, vboxsf_vnode** p, bool isRoot); + status_t vboxsf_get_vnode(fs_volume* volume, ino_t id, fs_vnode* vnode, int* _type, uint32* _flags, bool reenter); + status_t vboxsf_put_vnode(fs_volume* volume, fs_vnode* vnode, bool reenter); ++status_t vboxsf_remove_vnode(fs_volume* volume, fs_vnode* vnode, bool reenter); ++status_t vboxsf_delete_vnode(vboxsf_vnode* vnode); + PSHFLSTRING make_shflstring(const char* const s); + mode_t mode_from_fmode(RTFMODE fMode); + status_t vbox_err_to_haiku_err(int rc); + extern mutex g_vnodeCacheLock; ++extern fs_vnode_ops vboxsf_vnode_ops; + + #ifdef __cplusplus + } + #endif + ++ ++ + #endif /* !GA_INCLUDED_SRC_haiku_SharedFolders_vboxsf_h */ + +diff --git a/src/VBox/Additions/haiku/SharedFolders/vnode_cache.cpp b/src/VBox/Additions/haiku/SharedFolders/vnode_cache.cpp +index f419cc6..5d76475 100644 +--- a/src/VBox/Additions/haiku/SharedFolders/vnode_cache.cpp ++++ b/src/VBox/Additions/haiku/SharedFolders/vnode_cache.cpp +@@ -44,7 +44,9 @@ + */ + + #include "vboxsf.h" +-#include "OpenHashTable.h" ++#include ++ ++void* __dso_handle = NULL; + + struct HashTableDefinition + { +@@ -75,9 +77,9 @@ struct HashTableDefinition + static BOpenHashTable g_cache; + static ino_t g_nextVnid = 1; + mutex g_vnodeCacheLock; ++static vboxsf_vnode * current = NULL; + +- +-extern "C" status_t vboxsf_new_vnode(PVBSFMAP map, PSHFLSTRING path, PSHFLSTRING name, vboxsf_vnode** p) ++extern "C" status_t vboxsf_new_vnode(fs_volume* volume, PVBGLSFMAP map, PSHFLSTRING path, PSHFLSTRING name, ino_t parent, mode_t mode, vboxsf_vnode** p, bool isRoot) + { + vboxsf_vnode* vn = (vboxsf_vnode*)malloc(sizeof(vboxsf_vnode)); + if (vn == NULL) +@@ -85,7 +87,11 @@ extern "C" status_t vboxsf_new_vnode(PVBSFMAP map, PSHFLSTRING path, PSHFLSTRING + + dprintf("creating new vnode at %p with path=%p (%s)\n", vn, path->String.utf8, path->String.utf8); + vn->map = map; ++ vn->parentvnode = parent; ++ vn->mode = mode; + vn->path = path; ++ vn->next = NULL; ++ vn->int_next = NULL; + if (name) + vn->name = name; + else +@@ -104,31 +110,105 @@ extern "C" status_t vboxsf_new_vnode(PVBSFMAP map, PSHFLSTRING path, PSHFLSTRING + } + + vn->vnode = g_nextVnid++; ++ if (!isRoot) { ++ //acquire_vnode(volume, vn->vnode); ++ } + *p = vn; + dprintf("vboxsf: allocated %p (path=%p name=%p)\n", vn, vn->path, vn->name); + status_t rv = g_cache.Insert(vn); + +- mutex_unlock(&g_vnodeCacheLock); +- +- return rv; ++ if (current != NULL) ++ { ++ current->next = vn; ++ current->int_next = vn; ++ } else ++ { ++ dprintf("No current vnode\n"); ++ } ++ current = vn; ++ if (!isRoot) { ++ //get_vnode(volume, vn->vnode, NULL); ++ //unremove_vnode(volume, vn->vnode); ++ //put_vnode(volume, vn->vnode); ++ //put_vnode(volume, vn->vnode); ++ } ++ mutex_unlock(&g_vnodeCacheLock); ++ return rv; + } + + + extern "C" status_t vboxsf_get_vnode(fs_volume* volume, ino_t id, fs_vnode* vnode, + int* _type, uint32* _flags, bool reenter) + { ++ dprintf("vboxsf_get_vnode\n"); + vboxsf_vnode* vn = g_cache.Lookup(id); ++ dprintf("Performed lookup for %d\n", id); ++ _flags = 0; + if (vn) + { ++ dprintf("Found node, returning\n"); ++ + vnode->private_node = vn; ++ vnode->ops = &vboxsf_vnode_ops; ++ *_type = vn->mode; ++ + return B_OK; + } ++ dprintf("Failed to find node\n"); + return B_ERROR; + } + + + extern "C" status_t vboxsf_put_vnode(fs_volume* volume, fs_vnode* vnode, bool reenter) + { +- g_cache.Remove((vboxsf_vnode*)vnode->private_node); ++ vboxsf_volume* _volume = (vboxsf_volume*)volume->private_volume; ++ vboxsf_vnode* _vnode = (vboxsf_vnode*)vnode->private_node; ++ ++ dprintf("Call vboxsf_put_vnode %ld (%s)\n", _vnode->vnode, _vnode->path->String.utf8); ++ if (1 == _vnode->vnode) ++ { ++ return B_OK; ++ } ++ vboxsf_delete_vnode(_vnode); ++ ++ dprintf("Call vboxsf_put_vnode return OK\n"); ++ return B_OK; + } + ++extern "C" status_t vboxsf_remove_vnode(fs_volume* volume, fs_vnode* vnode, bool reenter) ++{ ++ dprintf("Call vboxsf_remove_vnode %d\n", reenter); ++ vboxsf_volume* _volume = (vboxsf_volume*)volume->private_volume; ++ vboxsf_vnode* _vnode = (vboxsf_vnode*)vnode->private_node; ++ ++ if (1 == _vnode->vnode) ++ { ++ return B_OK; ++ } ++ ++ vboxsf_delete_vnode(_vnode); ++ ++ dprintf("Call vboxsf_remove_vnode return OK\n"); ++ return B_OK; ++} ++ ++extern "C" status_t vboxsf_delete_vnode(vboxsf_vnode* vnode) ++{ ++ dprintf("Call vboxsf_delete_vnode (vboxsf_vnode)\n"); ++ // retain link to next entry ++ vboxsf_vnode* prev; ++ ino_t entry = vnode->vnode; ++ if (find_node_ancestor_by_ref(entry, &prev)) ++ { ++ prev->next = vnode->next; ++ prev->int_next = vnode->int_next; ++ } ++ if (current == vnode) ++ current = prev; ++ free(vnode->path); ++ g_cache.Remove(vnode); ++ free(vnode); ++ vnode = NULL; ++ dprintf("Call vboxsf_delete_vnode return OK\n"); ++ return B_OK; ++} +diff --git a/src/VBox/Additions/haiku/VBoxMouse/VBoxMouse.cpp b/src/VBox/Additions/haiku/VBoxMouse/VBoxMouse.cpp +index ee450b8..4ada6de 100644 +--- a/src/VBox/Additions/haiku/VBoxMouse/VBoxMouse.cpp ++++ b/src/VBox/Additions/haiku/VBoxMouse/VBoxMouse.cpp +@@ -48,8 +48,6 @@ + #include + #include + #include +-#include +-#include + #include + #include + +@@ -60,9 +58,10 @@ + #include + #include + #include ++#include + + /* Export as global symbol with C linkage, RTDECL is necessary. */ +-RTDECL(BInputServerDevice *) ++BInputServerDevice * + instantiate_input_device() + { + return new VBoxMouse(); +@@ -75,6 +74,7 @@ static inline int vboxMouseAcquire() + int rc = VbglR3GetMouseStatus(&fFeatures, NULL, NULL); + if (RT_SUCCESS(rc)) + { ++ fFeatures &= VMMDEV_MOUSE_GUEST_NEEDS_HOST_CURSOR; + rc = VbglR3SetMouseStatus(fFeatures | VMMDEV_MOUSE_GUEST_CAN_ABSOLUTE | VMMDEV_MOUSE_NEW_PROTOCOL); + if (RT_FAILURE(rc)) + LogRel(("VbglR3SetMouseStatus failed. rc=%d\n", rc)); +@@ -107,6 +107,8 @@ VBoxMouse::VBoxMouse() + fServiceThreadID(-1), + fExiting(false) + { ++ int rc = VbglR3Init(); ++ fInited = RT_SUCCESS(rc); + } + + +@@ -117,14 +119,12 @@ VBoxMouse::~VBoxMouse() + + status_t VBoxMouse::InitCheck() + { +- int rc = VbglR3Init(); +- if (!RT_SUCCESS(rc)) +- return ENXIO; ++ if (!fInited) ++ return ENXIO; + + input_device_ref device = { (char *)"VBoxMouse", B_POINTING_DEVICE, (void *)this }; + input_device_ref *deviceList[2] = { &device, NULL }; +- RegisterDevices(deviceList); +- ++ RegisterDevices(deviceList); + return B_OK; + } + +@@ -284,10 +284,10 @@ status_t VBoxMouse::_ServiceThread() + if ( RT_SUCCESS(rc) + && (fFeatures & VMMDEV_MOUSE_HOST_WANTS_ABSOLUTE)) + { +- float x = cx * 1.0 / 65535; ++ float x = cx * 1.0 / 65535; + float y = cy * 1.0 / 65535; + +- _debugPrintf("VBoxMouse: at %d,%d %f,%f\n", cx, cy, x, y); ++ //_debugPrintf("VBoxMouse: at %d,%d %f,%f\n", cx, cy, x, y); + + /* Send absolute movement */ + bigtime_t now = system_time(); +diff --git a/src/VBox/Additions/haiku/VBoxMouse/VBoxMouse.h b/src/VBox/Additions/haiku/VBoxMouse/VBoxMouse.h +index 9280a18..ae32828 100644 +--- a/src/VBox/Additions/haiku/VBoxMouse/VBoxMouse.h ++++ b/src/VBox/Additions/haiku/VBoxMouse/VBoxMouse.h +@@ -50,9 +50,10 @@ + # pragma once + #endif + ++#include + #include + +-extern "C" _EXPORT BInputServerDevice* instantiate_input_device(); ++extern "C" _EXPORT BInputServerDevice * instantiate_input_device(); + + class VBoxMouse : public BInputServerDevice + { +@@ -75,6 +76,7 @@ class VBoxMouse : public BInputServerDevice + int fDriverFD; + thread_id fServiceThreadID; + bool fExiting; ++ bool fInited; + }; + + #endif /* !GA_INCLUDED_SRC_haiku_VBoxMouse_VBoxMouse_h */ +diff --git a/src/VBox/Additions/haiku/VBoxTray/Makefile.kmk b/src/VBox/Additions/haiku/VBoxTray/Makefile.kmk +index eeb6989..7b0ae85 100644 +--- a/src/VBox/Additions/haiku/VBoxTray/Makefile.kmk ++++ b/src/VBox/Additions/haiku/VBoxTray/Makefile.kmk +@@ -52,23 +52,22 @@ include $(KBUILD_PATH)/subheader.kmk + + PROGRAMS += VBoxTray + VBoxTray_TEMPLATE = VBOXGUESTR3EXE +-VBoxTray_DEFS = VBOX_WITH_HGCM LOG_TO_BACKDOOR ++VBoxTray_TOOL = $(VBOX_GCC_TOOL) ++VBoxTray_DEFS = VBOX_WITH_SHARED_CLIPBOARD VBOX_WITH_HGCM LOG_TO_BACKDOOR + VBoxTray_DEFS += LOG_ENABLED + VBoxTray_INCS = ../include + VBoxTray_SOURCES = \ +- VBoxClipboard.cpp \ +- VBoxDisplay.cpp \ + VBoxGuestApplication.cpp \ +- VBoxGuestDeskbarView.cpp +- ++ VBoxGuestDeskbarView.cpp \ ++ VBoxClipboard.cpp \ ++ VBoxDisplay.cpp + VBoxTray_SOURCES += \ +- $(PATH_ROOT)/src/VBox/GuestHost/SharedClipboard/clipboard-helper.cpp ++ $(PATH_ROOT)/src/VBox/GuestHost/SharedClipboard/clipboard-common.cpp + + VBoxTray_LIBS = \ + be translation \ +- $(VBOX_LIB_VBGL_R3) \ + $(VBOX_LIB_IPRT_GUEST_R3) \ +- $(VBOX_LIB_VBGL_R3) ++ $(VBOX_LIB_VBGL_R3) + + VBoxTray_RSRCS += $(VBoxTray_0_OUTDIR)/VBoxTray.rsrc + VBoxTray_DEPS += $(VBoxTray_0_OUTDIR)/VBoxTray.rsrc +diff --git a/src/VBox/Additions/haiku/VBoxTray/VBoxClipboard.cpp b/src/VBox/Additions/haiku/VBoxTray/VBoxClipboard.cpp +index 87f2d01..4b0c081 100644 +--- a/src/VBox/Additions/haiku/VBoxTray/VBoxClipboard.cpp ++++ b/src/VBox/Additions/haiku/VBoxTray/VBoxClipboard.cpp +@@ -51,17 +51,20 @@ + #include + #include + #include ++#include + #include + #include + #include + #include + #include + +-#include "VBoxGuestApplication.h" + #include "VBoxClipboard.h" + #include + + #include ++#include ++#include ++#include + #include + #include + #include +@@ -255,7 +258,7 @@ void VBoxShClService::MessageReceived(BMessage *message) + if (formats & VBOX_SHCL_FMT_UNICODETEXT) + { + const char *text; +- int32 textLen; ++ ssize_t textLen; + if (clip->FindData("text/plain", B_MIME_TYPE, (const void **)&text, &textLen) == B_OK) + { + // usually doesn't include the \0 so be safe +@@ -314,7 +317,7 @@ void VBoxShClService::MessageReceived(BMessage *message) + { + printf("B_CLIPBOARD_CHANGED\n"); + const void *data; +- int32 dataLen; ++ ssize_t dataLen; + if (!be_clipboard->Lock()) + break; + +@@ -370,7 +373,7 @@ status_t VBoxShClService::_ServiceThread() + printf("VBoxShClService::%s()\n", __FUNCTION__); + + /* The thread waits for incoming messages from the host. */ +- for (;;) ++ while (!fExiting) + { + uint32_t u32Msg; + uint32_t u32Formats; +@@ -419,8 +422,6 @@ status_t VBoxShClService::_ServiceThread() + + LogRelFlow(("processed host event rc = %d\n", rc)); + +- if (fExiting) +- break; + } + return 0; + } +diff --git a/src/VBox/Additions/haiku/VBoxTray/VBoxDisplay.cpp b/src/VBox/Additions/haiku/VBoxTray/VBoxDisplay.cpp +index 2c38067..c8e2d3c 100644 +--- a/src/VBox/Additions/haiku/VBoxTray/VBoxDisplay.cpp ++++ b/src/VBox/Additions/haiku/VBoxTray/VBoxDisplay.cpp +@@ -54,13 +54,19 @@ + #include + #include + +-#include "VBoxGuestApplication.h" + #include "VBoxDisplay.h" + #include + #include "../VBoxVideo/common/VBoxVideo_common.h" + + #include + #include ++#include ++#include ++ ++#include ++#include /** @todo use the VbglR3 interface! */ ++#include ++ + + #ifdef DEBUG_ramshankar + # undef Log +@@ -123,8 +129,7 @@ status_t VBoxDisplayService::_ServiceThread() + { + uint32_t events; + int rc = VbglR3WaitEvent(VMMDEV_EVENT_DISPLAY_CHANGE_REQUEST, 5000, &events); +- if ( rc == VERR_TIMEOUT +- || rc == VERR_INTERRUPTED) ++ if ( rc == VERR_TIMEOUT || rc == VERR_INTERRUPTED) + continue; + + if (RT_SUCCESS(rc)) +diff --git a/src/VBox/Additions/haiku/VBoxTray/VBoxGuestApplication.cpp b/src/VBox/Additions/haiku/VBoxTray/VBoxGuestApplication.cpp +index 1c4587a..91983f4 100644 +--- a/src/VBox/Additions/haiku/VBoxTray/VBoxGuestApplication.cpp ++++ b/src/VBox/Additions/haiku/VBoxTray/VBoxGuestApplication.cpp +@@ -48,44 +48,37 @@ + /********************************************************************************************************************************* + * Header Files * + *********************************************************************************************************************************/ +-#include ++#include + +-#include +-#include +-#include +-#include +-#include +- +-#include "VBoxClipboard.h" +-#include "VBoxGuestApplication.h" ++#include + #include "VBoxGuestDeskbarView.h" + +-VBoxGuestApplication::VBoxGuestApplication() +- : BApplication(VBOX_GUEST_APP_SIG) +-{ +-} +- +- +-VBoxGuestApplication::~VBoxGuestApplication() ++status_t our_image(image_info & image) + { ++ team_id team = B_CURRENT_TEAM; ++ int32 cookie = 0; ++ ++ while (get_next_image_info(team, &cookie, &image) == B_OK) ++ { ++ if ((char *)our_image >= (char *)image.text ++ && (char *)our_image <= (char *)image.text + image.text_size) ++ return B_OK; ++ } ++ return B_ERROR; + } + +- +-void VBoxGuestApplication::ReadyToRun() +-{ +- status_t err; +- +- err = VBoxGuestDeskbarView::AddToDeskbar(); +- LogFlow(("VBoxGuestDeskbarView::ReadyToRun: AddToDeskbar returned 0x%08lx\n", err)); +- exit(0); +-} +- +- + int main(int argc, const char **argv) + { +- new VBoxGuestApplication(); +- be_app->Run(); +- delete be_app; ++ status_t err; ++ image_info info; ++ entry_ref ref; ++ ++ if (our_image(info) == B_OK && get_ref_for_path(info.name, &ref) == B_OK) { ++ BDeskbar deskbar; ++ if (!deskbar.IsRunning()) return 1; ++ //VBoxGuestDeskbarView * dv = new VBoxGuestDeskbarView(); ++ deskbar.AddItem(&ref); ++ } + return 0; + } + +diff --git a/src/VBox/Additions/haiku/VBoxTray/VBoxGuestApplication.h b/src/VBox/Additions/haiku/VBoxTray/VBoxGuestApplication.h +deleted file mode 100644 +index 0b6b6d2..0000000 +--- a/src/VBox/Additions/haiku/VBoxTray/VBoxGuestApplication.h ++++ /dev/null +@@ -1,79 +0,0 @@ +-/* $Id: VBoxGuestApplication.h $ */ +-/** @file +- * VBoxGuestApplication, Haiku Guest Additions, header. +- */ +- +-/* +- * Copyright (C) 2012-2020 Oracle Corporation +- * +- * This file is part of VirtualBox Open Source Edition (OSE), as +- * available from http://www.virtualbox.org. This file is free software; +- * you can redistribute it and/or modify it under the terms of the GNU +- * General Public License (GPL) as published by the Free Software +- * Foundation, in version 2 as it comes in the "COPYING" file of the +- * VirtualBox OSE distribution. VirtualBox OSE is distributed in the +- * hope that it will be useful, but WITHOUT ANY WARRANTY of any kind. +- */ +- +-/* +- * This code is based on: +- * +- * VirtualBox Guest Additions for Haiku. +- * Copyright (c) 2011 Mike Smith +- * François Revol +- * +- * Permission is hereby granted, free of charge, to any person +- * obtaining a copy of this software and associated documentation +- * files (the "Software"), to deal in the Software without +- * restriction, including without limitation the rights to use, +- * copy, modify, merge, publish, distribute, sublicense, and/or sell +- * copies of the Software, and to permit persons to whom the +- * Software is furnished to do so, subject to the following +- * conditions: +- * +- * The above copyright notice and this permission notice shall be +- * included in all copies or substantial portions of the Software. +- * +- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES +- * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +- * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +- * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR +- * OTHER DEALINGS IN THE SOFTWARE. +- */ +- +-#ifndef GA_INCLUDED_SRC_haiku_VBoxTray_VBoxGuestApplication_h +-#define GA_INCLUDED_SRC_haiku_VBoxTray_VBoxGuestApplication_h +-#ifndef RT_WITHOUT_PRAGMA_ONCE +-# pragma once +-#endif +- +-/** @todo r=ramshankar; why are we including all the headers here!?? Do it in +- * the .cpp please. */ +-#include +- +-#include +-#include +- +-#include +-#include +-#include /** @todo use the VbglR3 interface! */ +-#include +- +-#include +- +-class VBoxShClService; +- +-class VBoxGuestApplication : public BApplication +-{ +- public: +- VBoxGuestApplication(); +- virtual ~VBoxGuestApplication(); +- +- virtual void ReadyToRun(); +-}; +- +-#endif /* !GA_INCLUDED_SRC_haiku_VBoxTray_VBoxGuestApplication_h */ +- +diff --git a/src/VBox/Additions/haiku/VBoxTray/VBoxGuestDeskbarView.cpp b/src/VBox/Additions/haiku/VBoxTray/VBoxGuestDeskbarView.cpp +index 16f039e..18da3e4 100644 +--- a/src/VBox/Additions/haiku/VBoxTray/VBoxGuestDeskbarView.cpp ++++ b/src/VBox/Additions/haiku/VBoxTray/VBoxGuestDeskbarView.cpp +@@ -49,51 +49,35 @@ + * Header Files * + *********************************************************************************************************************************/ + #include +-#include +-#include +-#include + #include + #include ++#include + #include ++#include + #include + #include +-#include ++#include + #include + #include ++#include + ++#include + #include "VBoxGuestDeskbarView.h" +-#include "VBoxGuestApplication.h" + + #define VIEWNAME "VBoxGuestDeskbarView" + +-static status_t +-our_image(image_info& image) +-{ +- /** @todo r=ramshankar: find a way to do this without annoying the compiler, probably uintptr_t? */ +- int32 cookie = 0; +- while (get_next_image_info(B_CURRENT_TEAM, &cookie, &image) == B_OK) +- { +- if ((char *)our_image >= (char *)image.text +- && (char *)our_image <= (char *)image.text + image.text_size) +- return B_OK; +- } +- +- return B_ERROR; +-} +- +- + VBoxGuestDeskbarView::VBoxGuestDeskbarView() +- : BView(BRect(0, 0, 15, 15), VIEWNAME, B_FOLLOW_NONE, ++ : BView(BRect(0, 0, B_MINI_ICON - 1, B_MINI_ICON - 1),VIEWNAME, B_FOLLOW_ALL, + B_WILL_DRAW | B_NAVIGABLE), +- fIcon(NULL), fClipboardService(NULL), fDisplayService(NULL) ++ fIcon(NULL), fClipboardService(NULL), fDisplayService(NULL), inited(false) + { +- _Init(); ++ //_Init(); + } + + + VBoxGuestDeskbarView::VBoxGuestDeskbarView(BMessage *archive) + : BView(archive), +- fIcon(NULL) ++ fIcon(NULL), fClipboardService(NULL), fDisplayService(NULL), inited(false) + { + archive->PrintToStream(); + _Init(archive); +@@ -102,16 +86,42 @@ VBoxGuestDeskbarView::VBoxGuestDeskbarView(BMessage *archive) + + VBoxGuestDeskbarView::~VBoxGuestDeskbarView() + { +- delete fIcon; +- if (fClipboardService) +- { +- fClipboardService->Disconnect(); +- delete fClipboardService; ++ if (fIcon) ++ delete fIcon; ++ BMessage message(B_QUIT_REQUESTED); ++ if (fDisplayService) { ++ fDisplayService->MessageReceived(&message); ++ //fDisplayService->Stop(); ++ delete fDisplayService; ++ fDisplayService = NULL; + } +- VbglR3Term(); ++ if (fClipboardService) ++ { ++ fClipboardService->MessageReceived(&message); ++ fClipboardService->Disconnect(); ++ delete fClipboardService; ++ fClipboardService = NULL; ++ } ++ ++ if (inited) { ++ VbglR3Term(); ++ inited = false; ++ } + } + + ++BBitmap * get_resource_bitmap() ++{ ++ entry_ref ref; ++ BBitmap *bmp = new BBitmap(BRect(0,0, B_MINI_ICON-1, B_MINI_ICON-1), B_CMAP8); ++ if (be_roster->FindApp(VBOX_GUEST_APP_SIG, &ref) != B_OK) return NULL; ++ BNode file(&ref); ++ BNodeInfo *info = new BNodeInfo(&file); ++ info->GetIcon(bmp, B_MINI_ICON); ++ delete info; ++ return bmp; ++} ++ + BArchivable* VBoxGuestDeskbarView::Instantiate(BMessage *data) + { + if (!validate_instantiation(data, VIEWNAME)) +@@ -124,35 +134,30 @@ BArchivable* VBoxGuestDeskbarView::Instantiate(BMessage *data) + status_t VBoxGuestDeskbarView::Archive(BMessage *data, bool deep) const + { + status_t err; +- +- err = BView::Archive(data, false); +- if (err < B_OK) +- { +- LogRel(("VBoxGuestDeskbarView::Archive failed.rc=%08lx\n", err)); +- return err; +- } ++ err = BView::Archive(data, deep); + data->AddString("add_on", VBOX_GUEST_APP_SIG); +- data->AddString("class", "VBoxGuestDeskbarView"); +- return B_OK; ++ data->AddString("class", VIEWNAME); ++ return err; + } + + + void VBoxGuestDeskbarView::Draw(BRect rect) + { + SetDrawingMode(B_OP_ALPHA); +- DrawBitmap(fIcon); ++ if (fIcon != NULL) ++ DrawBitmap(fIcon); + } + + + void VBoxGuestDeskbarView::AttachedToWindow() + { + BView::AttachedToWindow(); ++ + if (Parent()) + { + SetViewColor(Parent()->ViewColor()); + SetLowColor(Parent()->LowColor()); + } +- + if (fClipboardService) /* Don't repeatedly crash deskbar if vboxdev not loaded */ + { + Looper()->AddHandler(fClipboardService); +@@ -166,21 +171,16 @@ void VBoxGuestDeskbarView::AttachedToWindow() + + void VBoxGuestDeskbarView::DetachedFromWindow() + { +- BMessage message(B_QUIT_REQUESTED); +- fClipboardService->MessageReceived(&message); +- fDisplayService->MessageReceived(&message); ++ + } + + +-void VBoxGuestDeskbarView::MouseDown(BPoint point) ++void VBoxGuestDeskbarView::MouseDown(BPoint pt) + { +- int32 buttons = B_PRIMARY_MOUSE_BUTTON; +- if (Looper() != NULL && Looper()->CurrentMessage() != NULL) +- Looper()->CurrentMessage()->FindInt32("buttons", &buttons); +- +- BPoint where = ConvertToScreen(point); +- +- if ((buttons & B_SECONDARY_MOUSE_BUTTON) != 0) ++ BPoint point; ++ uint32 buttons; ++ GetMouse(&point, &buttons); ++ if ((buttons != B_SECONDARY_MOUSE_BUTTON)) + { + BPopUpMenu *menu = new BPopUpMenu(B_EMPTY_STRING, false, false); + menu->SetAsyncAutoDestruct(true); +@@ -188,99 +188,77 @@ void VBoxGuestDeskbarView::MouseDown(BPoint point) + + menu->AddItem(new BMenuItem("Quit", new BMessage(B_QUIT_REQUESTED))); + menu->SetTargetForItems(this); ++ BRect bounds = Bounds(); ++ pt = ConvertToScreen(pt); ++ bounds = ConvertToScreen(bounds); + +- menu->Go(where, true, true, true); ++ menu->Go(pt, true, true, true); + } ++ + } + + + void VBoxGuestDeskbarView::MessageReceived(BMessage *message) + { + if (message->what == B_QUIT_REQUESTED) +- RemoveFromDeskbar(); +- else +- BHandler::MessageReceived(message); +-} +- +- +-status_t VBoxGuestDeskbarView::AddToDeskbar(bool force) +-{ +- BDeskbar deskbar; +- status_t err; ++ { ++ Looper()->Lock(); ++ Looper()->RemoveHandler(fClipboardService); ++ Looper()->Unlock(); + +- if (force) + RemoveFromDeskbar(); +- else if (deskbar.HasItem(VIEWNAME)) +- return B_OK; +- +- app_info info; +- err = be_app->GetAppInfo(&info); +- if (err < B_OK) +- return err; +- +- BPath p(&info.ref); +- return deskbar.AddItem(&info.ref); ++ } ++ else ++ BView::MessageReceived(message); + } + +- + status_t VBoxGuestDeskbarView::RemoveFromDeskbar() + { + BDeskbar deskbar; + return deskbar.RemoveItem(VIEWNAME); + } + +- + status_t VBoxGuestDeskbarView::_Init(BMessage *archive) + { +- BString toolTipText; ++ fIcon=NULL; ++ fClipboardService=NULL; ++ fDisplayService=NULL; ++ ++ BString toolTipText; + toolTipText << VBOX_PRODUCT << " Guest Additions "; + toolTipText << VBOX_VERSION_MAJOR << "." << VBOX_VERSION_MINOR << "." << VBOX_VERSION_BUILD; + toolTipText << "r" << VBOX_SVN_REV; + + SetToolTip(toolTipText.String()); +- +- image_info info; +- if (our_image(info) != B_OK) +- return B_ERROR; +- +- BFile file(info.name, B_READ_ONLY); +- if (file.InitCheck() < B_OK) +- return B_ERROR; +- +- BResources resources(&file); +- if (resources.InitCheck() < B_OK) +- return B_ERROR; +- +- const void *data = NULL; +- size_t size; +- //data = resources.LoadResource(B_VECTOR_ICON_TYPE, +- // kNetworkStatusNoDevice + i, &size); +- data = resources.LoadResource('data', 400, &size); +- if (data != NULL) +- { +- BMemoryIO mem(data, size); +- fIcon = BTranslationUtils::GetBitmap(&mem); +- } +- +- int rc = RTR3InitDll(RTR3INIT_FLAGS_UNOBTRUSIVE); ++ fIcon = get_resource_bitmap(); ++ ++ int rc = RTR3InitExeNoArguments(0); //(RTR3INIT_FLAGS_UNOBTRUSIVE); + if (RT_SUCCESS(rc)) + { +- rc = VbglR3Init(); ++ if (!inited) ++ rc = VbglR3Init(); + if (RT_SUCCESS(rc)) + { ++ inited = true; + fClipboardService = new VBoxShClService(); ++ //disabled as not supported currently and causes segfault on exit + fDisplayService = new VBoxDisplayService(); + } + else +- LogRel(("VBoxGuestDeskbarView::_init VbglR3Init failed. rc=%d\n", rc)); ++ { ++ //syslog(LOG_ERR,"VBoxGuestDeskbarView::_init VbglR3Init failed. rc=%d\n", rc); ++ } + } + else +- LogRel(("VBoxGuestDeskbarView::_init RTR3InitDll failed. rc=%d\n", rc)); +- return RTErrConvertToErrno(rc); ++ { ++ //syslog(LOG_ERR,"VBoxGuestDeskbarView::_init RTR3InitDll failed. rc=%d\n", rc); ++ } ++ ++ return B_OK; + } + + +-RTDECL(BView*) instantiate_deskbar_item() ++BView* instantiate_deskbar_item() + { + return new VBoxGuestDeskbarView(); + } +diff --git a/src/VBox/Additions/haiku/VBoxTray/VBoxGuestDeskbarView.h b/src/VBox/Additions/haiku/VBoxTray/VBoxGuestDeskbarView.h +index da817a5..6bf6396 100644 +--- a/src/VBox/Additions/haiku/VBoxTray/VBoxGuestDeskbarView.h ++++ b/src/VBox/Additions/haiku/VBoxTray/VBoxGuestDeskbarView.h +@@ -65,6 +65,8 @@ + #include "VBoxClipboard.h" + #include "VBoxDisplay.h" + ++extern "C" _EXPORT BView *instantiate_deskbar_item(); ++ + #define REMOVE_FROM_DESKBAR_MSG 'vbqr' + + class VBoxGuestDeskbarView : public BView +@@ -72,19 +74,18 @@ class VBoxGuestDeskbarView : public BView + public: + VBoxGuestDeskbarView(); + VBoxGuestDeskbarView(BMessage *archive); +- virtual ~VBoxGuestDeskbarView(); ++ ~VBoxGuestDeskbarView(); + + static BArchivable* Instantiate(BMessage *data); +- virtual status_t Archive(BMessage *data, bool deep = true) const; ++ status_t Archive(BMessage *data, bool deep = true) const; + + void Draw(BRect rect); + void AttachedToWindow(); + void DetachedFromWindow(); + +- virtual void MouseDown(BPoint point); +- virtual void MessageReceived(BMessage *message); ++ void MouseDown(BPoint point); ++ void MessageReceived(BMessage *message); + +- static status_t AddToDeskbar(bool force = true); + static status_t RemoveFromDeskbar(); + + private: +@@ -93,6 +94,7 @@ class VBoxGuestDeskbarView : public BView + + VBoxShClService *fClipboardService; + VBoxDisplayService *fDisplayService; ++ bool inited; + }; + + #endif /* !GA_INCLUDED_SRC_haiku_VBoxTray_VBoxGuestDeskbarView_h */ +diff --git a/src/VBox/Additions/haiku/VBoxTray/VBoxTray.rdef b/src/VBox/Additions/haiku/VBoxTray/VBoxTray.rdef +index 4d7e30b..c8d8a63 100644 +--- a/src/VBox/Additions/haiku/VBoxTray/VBoxTray.rdef ++++ b/src/VBox/Additions/haiku/VBoxTray/VBoxTray.rdef +@@ -42,10 +42,9 @@ + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + */ ++#include "VBoxGuestInternal.h" + +-#include "VBoxGuestInternal.h" +- +-resource(1, "BEOS:APP_SIG") #'MIMS' VBOX_GUEST_APP_SIG; ++resource app_signature VBOX_GUEST_APP_SIG; + + resource app_flags B_SINGLE_LAUNCH; + +@@ -59,7 +58,7 @@ resource app_version { + internal = VBOX_SVN_REV, + + short_info = VBOX_PRODUCT, +- long_info = VBOX_PRODUCT " " VBOX_VERSION_STRING " ©2009-" VBOX_C_YEAR " " VBOX_VENDOR ++ long_info = VBOX_PRODUCT " " VBOX_VERSION_STRING " ©2009-" VBOX_C_YEAR " " VBOX_VENDOR + }; + */ + +@@ -79,5 +78,3 @@ resource vector_icon { + $"D10000000000003F45D1C70BA246F45D0117820004" + }; + +-resource(400, "DeskbarShelfIcon.png") #'data' import VBOX_HAIKU_DESKBAR_ICON_PNG; +- +diff --git a/src/VBox/Additions/haiku/VBoxVideo/accelerant/accelerant.cpp b/src/VBox/Additions/haiku/VBoxVideo/accelerant/accelerant.cpp +index 33832ae..050e040 100644 +--- a/src/VBox/Additions/haiku/VBoxVideo/accelerant/accelerant.cpp ++++ b/src/VBox/Additions/haiku/VBoxVideo/accelerant/accelerant.cpp +@@ -62,6 +62,7 @@ AccelerantInfo gInfo; + static engine_token sEngineToken = { 1, 0 /*B_2D_ACCELERATION*/, NULL }; + + /** @todo r=ramshankar: get rid of this and replace with IPRT logging. */ ++#ifdef ENABLE_DEBUG_TRACE + #define TRACE(x...) do { \ + FILE* logfile = fopen("/var/log/vboxvideo.accelerant.log", "a"); \ + fprintf(logfile, x); \ +@@ -70,6 +71,10 @@ static engine_token sEngineToken = { 1, 0 /*B_2D_ACCELERATION*/, NULL }; + fclose(logfile); \ + sync(); \ + } while(0) ++#else ++#define TRACE(x...) ; ++#endif ++ + + class AreaCloner + { +diff --git a/src/VBox/Additions/haiku/VBoxVideo/driver/Makefile.kmk b/src/VBox/Additions/haiku/VBoxVideo/driver/Makefile.kmk +index 9fb1942..bbb1625 100644 +--- a/src/VBox/Additions/haiku/VBoxVideo/driver/Makefile.kmk ++++ b/src/VBox/Additions/haiku/VBoxVideo/driver/Makefile.kmk +@@ -66,7 +66,7 @@ vboxvideo_DEFS = \ + KBUILD_MODNAME=KBUILD_STR\(VBoxVideo\) \ + KBUILD_BASENAME=KBUILD_STR\(VBoxVideo\) + vboxvideo_INCS = \ +- $(PATH_ROOT)/src/VBox/Additions/common/VBoxGuestLib \ ++ $(PATH_ROOT)/src/VBox/Additions/common/VBoxGuest/Lib \ + $(PATH_ROOT)/src/VBox/Additions/common/VBoxGuest \ + $(PATH_ROOT)/src/VBox/Runtime/r0drv/haiku \ + $(VBOX_GRAPHICS_INCS) +diff --git a/src/VBox/Additions/haiku/VBoxVideo/driver/driver.cpp b/src/VBox/Additions/haiku/VBoxVideo/driver/driver.cpp +index f2df235..7a3c7b4 100644 +--- a/src/VBox/Additions/haiku/VBoxVideo/driver/driver.cpp ++++ b/src/VBox/Additions/haiku/VBoxVideo/driver/driver.cpp +@@ -67,7 +67,7 @@ + * replace with IPRT version later. */ + #define ROUND_TO_PAGE_SIZE(x) (((x) + (B_PAGE_SIZE) - 1) & ~((B_PAGE_SIZE) - 1)) + +-#define ENABLE_DEBUG_TRACE ++//define ENABLE_DEBUG_TRACE + + #undef TRACE + #ifdef ENABLE_DEBUG_TRACE +@@ -171,10 +171,10 @@ status_t init_hardware() + if (err == B_OK) + return B_OK; + +- LogRel((DRIVER_NAME ":_init_hardware() get_module(%s) failed. err=%08lx\n", B_PCI_MODULE_NAME)); ++ Log((DRIVER_NAME ":_init_hardware() get_module(%s) failed. err=%08lx\n", B_PCI_MODULE_NAME)); + } + else +- LogRel((DRIVER_NAME ":_init_hardware() get_module(%s) failed. err=%08lx\n", VBOXGUEST_MODULE_NAME, err)); ++ Log((DRIVER_NAME ":_init_hardware() get_module(%s) failed. err=%08lx\n", VBOXGUEST_MODULE_NAME, err)); + return B_ERROR; + } + +@@ -203,7 +203,7 @@ status_t init_driver() + gDeviceInfo.sharedArea = create_area("vboxvideo shared info", + (void **)&gDeviceInfo.sharedInfo, B_ANY_KERNEL_ADDRESS, + ROUND_TO_PAGE_SIZE(sharedSize), B_FULL_LOCK, +- B_KERNEL_READ_AREA | B_KERNEL_WRITE_AREA | B_USER_CLONEABLE_AREA); ++ B_KERNEL_READ_AREA | B_KERNEL_WRITE_AREA | B_CLONEABLE_AREA); + + uint16_t width, height, vwidth, bpp, flags; + VBoxVideoGetModeRegisters(&width, &height, &vwidth, &bpp, &flags); +diff --git a/src/VBox/Runtime/common/misc/thread.cpp b/src/VBox/Runtime/common/misc/thread.cpp +index 604dd04..eeb83e3 100644 +--- a/src/VBox/Runtime/common/misc/thread.cpp ++++ b/src/VBox/Runtime/common/misc/thread.cpp +@@ -51,8 +51,11 @@ + #ifdef RT_WITH_ICONV_CACHE + # include "internal/string.h" + #endif +- +- ++#include ++#define _KERNEL_MODE 1 ++#include ++#include ++#include + /********************************************************************************************************************************* + * Defined Constants And Macros * + *********************************************************************************************************************************/ +@@ -394,9 +397,11 @@ PRTTHREADINT rtThreadAlloc(RTTHREADTYPE enmType, unsigned fFlags, uint32_t fIntF + #ifdef RT_WITH_ICONV_CACHE + rtStrIconvCacheInit(pThread); + #endif ++ + rc = RTSemEventMultiCreate(&pThread->EventUser); + if (RT_SUCCESS(rc)) + { ++ + rc = RTSemEventMultiCreate(&pThread->EventTerminated); + if (RT_SUCCESS(rc)) + return pThread; +@@ -576,7 +581,6 @@ DECLHIDDEN(PRTTHREADINT) rtThreadGet(RTTHREAD Thread) + DECLHIDDEN(uint32_t) rtThreadRelease(PRTTHREADINT pThread) + { + uint32_t cRefs; +- + Assert(pThread); + if (pThread->cRefs >= 1) + { +@@ -725,7 +729,6 @@ DECLCALLBACK(DECLHIDDEN(int)) rtThreadMain(PRTTHREADINT pThread, RTNATIVETHREAD + */ + rtThreadSetState(pThread, RTTHREADSTATE_RUNNING); + rc = pThread->pfnThread(pThread, pThread->pvUser); +- + /* + * Paranoia checks for leftover resources. + */ +@@ -801,9 +804,8 @@ RTDECL(int) RTThreadCreate(PRTTHREAD pThread, PFNRTTHREAD pfnThread, void *pvUse + pThreadInt->pfnThread = pfnThread; + pThreadInt->pvUser = pvUser; + pThreadInt->cbStack = cbStack; +- +- rc = rtThreadNativeCreate(pThreadInt, &NativeThread); +- if (RT_SUCCESS(rc)) ++ rc = rtThreadNativeCreate(pThreadInt, &NativeThread); ++ if (RT_SUCCESS(rc)) + { + rtThreadInsert(pThreadInt, NativeThread); + rtThreadRelease(pThreadInt); +diff --git a/src/VBox/Runtime/r0drv/haiku/alloc-r0drv-haiku.c b/src/VBox/Runtime/r0drv/haiku/alloc-r0drv-haiku.c +index 90fe0ce..9e9d111 100644 +--- a/src/VBox/Runtime/r0drv/haiku/alloc-r0drv-haiku.c ++++ b/src/VBox/Runtime/r0drv/haiku/alloc-r0drv-haiku.c +@@ -86,7 +86,7 @@ RTR0DECL(void *) RTMemContAlloc(PRTCCPHYS pPhys, size_t cb) RT_NO_THROW_DEF + * Allocate the memory and ensure that the API is still providing + * memory that's always below 4GB. + */ +- cb = RT_ALIGN_Z(cb, PAGE_SIZE); ++ cb = RT_ALIGN_Z(cb, B_PAGE_SIZE); + void *pv; + area_id area = create_area("VirtualBox Contig Alloc", &pv, B_ANY_KERNEL_ADDRESS, cb, B_32_BIT_CONTIGUOUS, + B_READ_AREA | B_WRITE_AREA); +diff --git a/src/VBox/Runtime/r0drv/haiku/memobj-r0drv-haiku.c b/src/VBox/Runtime/r0drv/haiku/memobj-r0drv-haiku.c +index 864078e..306cd69 100644 +--- a/src/VBox/Runtime/r0drv/haiku/memobj-r0drv-haiku.c ++++ b/src/VBox/Runtime/r0drv/haiku/memobj-r0drv-haiku.c +@@ -188,6 +188,7 @@ static int rtR0MemObjNativeAllocArea(PPRTR0MEMOBJINTERNAL ppMem, size_t cb, + /** @todo alignment */ + if (uAlignment != PAGE_SIZE) + return VERR_NOT_SUPPORTED; ++ break; + /** @todo r=ramshankar: no 'break' here?? */ + case RTR0MEMOBJTYPE_PHYS_NC: + pszName = "IPRT R0MemObj AllocPhys"; +diff --git a/src/VBox/Runtime/r0drv/haiku/semeventmulti-r0drv-haiku.c b/src/VBox/Runtime/r0drv/haiku/semeventmulti-r0drv-haiku.c +index 9c4b121..cbbbf41 100644 +--- a/src/VBox/Runtime/r0drv/haiku/semeventmulti-r0drv-haiku.c ++++ b/src/VBox/Runtime/r0drv/haiku/semeventmulti-r0drv-haiku.c +@@ -77,7 +77,7 @@ RTDECL(int) RTSemEventMultiCreateEx(PRTSEMEVENTMULTI phEventMultiSem, uint32_t + pThis->u32Magic = RTSEMEVENTMULTI_MAGIC; + pThis->cRefs = 1; + pThis->SemId = create_sem(0, "IPRT Semaphore Event Multi"); +- if (pThis->SemId < B_OK) ++ if (pThis->SemId >= B_OK) + { + set_sem_owner(pThis->SemId, B_SYSTEM_TEAM); + *phEventMultiSem = pThis; +@@ -85,7 +85,7 @@ RTDECL(int) RTSemEventMultiCreateEx(PRTSEMEVENTMULTI phEventMultiSem, uint32_t + } + + RTMemFree(pThis); +- return VERR_TOO_MANY_SEMAPHORES; /** @todo r=ramshankar: use RTErrConvertFromHaikuKernReturn */ ++ return VERR_NO_MEMORY; /** @todo r=ramshankar: use RTErrConvertFromHaikuKernReturn */ + } + + +diff --git a/src/VBox/Runtime/r0drv/haiku/semmutex-r0drv-haiku.c b/src/VBox/Runtime/r0drv/haiku/semmutex-r0drv-haiku.c +index fd6d0b3..7fc1fbd 100644 +--- a/src/VBox/Runtime/r0drv/haiku/semmutex-r0drv-haiku.c ++++ b/src/VBox/Runtime/r0drv/haiku/semmutex-r0drv-haiku.c +@@ -40,7 +40,10 @@ + #include + + #include "internal/magics.h" +- ++#define _KERNEL_MODE 1 ++#include ++#include ++#include + + /********************************************************************************************************************************* + * Structures and Typedefs * +@@ -70,11 +73,12 @@ RTDECL(int) RTSemMutexCreate(PRTSEMMUTEX phMutexSem) + + PRTSEMMUTEXINTERNAL pThis = (PRTSEMMUTEXINTERNAL)RTMemAllocZ(sizeof(*pThis)); + if (RT_UNLIKELY(!pThis)) ++ { + return VERR_NO_MEMORY; +- ++ } + pThis->u32Magic = RTSEMMUTEX_MAGIC; +- pThis->SemId = create_sem(0, "IPRT Mutex Semaphore"); +- if (pThis->SemId < B_OK) ++ pThis->SemId = create_sem(1, "IPRT Mutex Semaphore"); ++ if (pThis->SemId >= B_OK) + { + pThis->OwnerId = -1; + pThis->cRecursion = 0; +@@ -107,12 +111,11 @@ RTDECL(int) RTSemMutexDestroy(RTSEMMUTEX hMutexSem) + * Worker function for acquiring the mutex. + * + * @param hMutexSem The mutex object. +- * @param fFlags Mutex flags (see RTSEMWAIT_FLAGS_*) + * @param uTimeout Timeout in units specified by the flags. + * + * @return IPRT status code. + */ +-static int rtSemMutexRequestEx(RTSEMMUTEX hMutexSem, uint32_t fFlags, uint64_t uTimeout) ++static int rtSemMutexRequestEx(RTSEMMUTEX hMutexSem, uint64_t uTimeout) + { + PRTSEMMUTEXINTERNAL pThis = hMutexSem; + int rc; +@@ -124,31 +127,23 @@ static int rtSemMutexRequestEx(RTSEMMUTEX hMutexSem, uint32_t fFlags, uint64_t u + + if (pThis->OwnerId == find_thread(NULL)) + { +- pThis->OwnerId++; ++ pThis->cRecursion++; + return VINF_SUCCESS; + } + +- if (fFlags & RTSEMWAIT_FLAGS_INDEFINITE) ++ if (uTimeout == RT_INDEFINITE_WAIT) ++ { + timeout = B_INFINITE_TIMEOUT; ++ flags |= B_TIMEOUT; ++ } + else + { +- if (fFlags & RTSEMWAIT_FLAGS_NANOSECS) +- timeout = uTimeout / 1000; +- else if (fFlags & RTSEMWAIT_FLAGS_MILLISECS) +- timeout = uTimeout * 1000; +- else +- return VERR_INVALID_PARAMETER; +- +- if (fFlags & RTSEMWAIT_FLAGS_RELATIVE) +- flags |= B_RELATIVE_TIMEOUT; +- else if (fFlags & RTSEMWAIT_FLAGS_ABSOLUTE) +- flags |= B_ABSOLUTE_TIMEOUT; +- else +- return VERR_INVALID_PARAMETER; ++ // may need to revisit this ++ timeout = uTimeout * 1000; ++ flags |= B_RELATIVE_TIMEOUT; + } + +- if (fFlags & RTSEMWAIT_FLAGS_INTERRUPTIBLE) +- flags |= B_CAN_INTERRUPT; ++ flags |= B_CAN_INTERRUPT; + + status = acquire_sem_etc(pThis->SemId, 1, flags, timeout); + +@@ -174,14 +169,13 @@ static int rtSemMutexRequestEx(RTSEMMUTEX hMutexSem, uint32_t fFlags, uint64_t u + rc = VERR_INVALID_PARAMETER; + break; + } +- + return rc; + } + + + RTDECL(int) RTSemMutexRequest(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies) + { +- return rtSemMutexRequestEx(hMutexSem, RTSEMWAIT_FLAGS_RELATIVE | RTSEMWAIT_FLAGS_RESUME | RTSEMWAIT_FLAGS_MILLISECS, cMillies); ++ return rtSemMutexRequestEx(hMutexSem, cMillies); + } + + +@@ -193,7 +187,7 @@ RTDECL(int) RTSemMutexRequestDebug(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies, + + RTDECL(int) RTSemMutexRequestNoResume(RTSEMMUTEX hMutexSem, RTMSINTERVAL cMillies) + { +- return rtSemMutexRequestEx(hMutexSem, RTSEMWAIT_FLAGS_RELATIVE | RTSEMWAIT_FLAGS_NORESUME | RTSEMWAIT_FLAGS_MILLISECS, cMillies); ++ return rtSemMutexRequestEx(hMutexSem, cMillies); + } + + +diff --git a/src/VBox/Runtime/r0drv/haiku/the-haiku-kernel.h b/src/VBox/Runtime/r0drv/haiku/the-haiku-kernel.h +index 602d3aa..1f07364 100644 +--- a/src/VBox/Runtime/r0drv/haiku/the-haiku-kernel.h ++++ b/src/VBox/Runtime/r0drv/haiku/the-haiku-kernel.h +@@ -61,6 +61,7 @@ extern area_id vm_clone_area(team_id team, const char *name, void **address, uin + extern spinlock gThreadSpinlock; + #define GRAB_THREAD_LOCK() acquire_spinlock(&gThreadSpinlock) + #define RELEASE_THREAD_LOCK() release_spinlock(&gThreadSpinlock) ++#if 0 + typedef struct + { + int32 flags; /* summary of events relevant in interrupt handlers (signals pending, user debugging +@@ -85,9 +86,9 @@ typedef struct + + extern Thread* thread_get_thread_struct(thread_id id); + extern Thread* thread_get_thread_struct_locked(thread_id id); ++#endif + + extern void thread_yield(bool force); +- + RT_C_DECLS_END + + /** +diff --git a/src/VBox/Runtime/r0drv/haiku/thread-r0drv-haiku.c b/src/VBox/Runtime/r0drv/haiku/thread-r0drv-haiku.c +index ec8edeb..e919291 100644 +--- a/src/VBox/Runtime/r0drv/haiku/thread-r0drv-haiku.c ++++ b/src/VBox/Runtime/r0drv/haiku/thread-r0drv-haiku.c +@@ -39,7 +39,6 @@ + #include + #include + +- + RTDECL(RTNATIVETHREAD) RTThreadNativeSelf(void) + { + return (RTNATIVETHREAD)find_thread(NULL); +diff --git a/src/VBox/Runtime/r0drv/haiku/thread2-r0drv-haiku.c b/src/VBox/Runtime/r0drv/haiku/thread2-r0drv-haiku.c +index c2c13f9..1ce145d 100644 +--- a/src/VBox/Runtime/r0drv/haiku/thread2-r0drv-haiku.c ++++ b/src/VBox/Runtime/r0drv/haiku/thread2-r0drv-haiku.c +@@ -38,7 +38,10 @@ + #include + #include + #include "internal/thread.h" +- ++#include ++#include ++#include ++#include + + DECLHIDDEN(int) rtThreadNativeInit(void) + { +@@ -74,8 +77,9 @@ DECLHIDDEN(int) rtThreadNativeSetPriority(PRTTHREADINT pThread, RTTHREADTYPE enm + AssertMsgFailed(("enmType=%d\n", enmType)); + return VERR_INVALID_PARAMETER; + } +- + status = set_thread_priority((thread_id)pThread->Core.Key, iPriority); ++ if (status>B_OK) ++ return VINF_SUCCESS; + + return RTErrConvertFromHaikuKernReturn(status); + } +@@ -127,10 +131,12 @@ DECLHIDDEN(int) rtThreadNativeCreate(PRTTHREADINT pThreadInt, PRTNATIVETHREAD pN + RT_ASSERT_PREEMPTIBLE(); + + NativeThread = spawn_kernel_thread(rtThreadNativeMain, pThreadInt->szName, B_NORMAL_PRIORITY, pThreadInt); +- if (NativeThread >= B_OK) ++ ++ if (NativeThread >= 0) + { + resume_thread(NativeThread); + *pNativeThread = (RTNATIVETHREAD)NativeThread; ++ + return VINF_SUCCESS; + } + return RTErrConvertFromHaikuKernReturn(NativeThread); +diff --git a/src/VBox/Runtime/r3/posix/process-creation-posix.cpp b/src/VBox/Runtime/r3/posix/process-creation-posix.cpp +index c7402da..63f36de 100644 +--- a/src/VBox/Runtime/r3/posix/process-creation-posix.cpp ++++ b/src/VBox/Runtime/r3/posix/process-creation-posix.cpp +@@ -104,6 +104,11 @@ + # include + #endif + ++#ifdef RT_OS_HAIKU ++#define _BSD_SOURCE ++# include ++#endif ++ + #ifndef RT_OS_SOLARIS + # include + #else +diff --git a/src/VBox/Runtime/r3/posix/serialport-posix.cpp b/src/VBox/Runtime/r3/posix/serialport-posix.cpp +index fba73ac..934f671 100644 +--- a/src/VBox/Runtime/r3/posix/serialport-posix.cpp ++++ b/src/VBox/Runtime/r3/posix/serialport-posix.cpp +@@ -581,6 +581,7 @@ static int rtSerialPortTermios2Cfg(PRTSERIALPORTINTERNAL pThis, struct termios * + + switch (pTermios->c_cflag & CSIZE) + { ++#ifndef RT_OS_HAIKU + case CS5: + pCfg->enmDataBitCount = RTSERIALPORTDATABITS_5BITS; + f5DataBits = true; +@@ -591,6 +592,7 @@ static int rtSerialPortTermios2Cfg(PRTSERIALPORTINTERNAL pThis, struct termios * + case CS7: + pCfg->enmDataBitCount = RTSERIALPORTDATABITS_7BITS; + break; ++#endif + case CS8: + pCfg->enmDataBitCount = RTSERIALPORTDATABITS_8BITS; + break; +@@ -660,6 +662,9 @@ DECLINLINE(int) rtSerialPortWakeupEvtPoller(PRTSERIALPORTINTERNAL pThis, uint8_t + */ + static DECLCALLBACK(int) rtSerialPortStsLineMonitorThrd(RTTHREAD hThreadSelf, void *pvUser) + { ++#ifdef RT_OS_HAIKU ++ #define TIOCM_RNG TIOCM_RI ++#endif + RT_NOREF(hThreadSelf); + PRTSERIALPORTINTERNAL pThis = (PRTSERIALPORTINTERNAL)pvUser; + unsigned long const fStsLinesChk = TIOCM_CAR | TIOCM_RNG | TIOCM_DSR | TIOCM_CTS; +-- +2.30.2 + diff --git a/app-emulation/virtualbox-guest-additions/virtualbox_guest_additions-6.1.26.recipe b/app-emulation/virtualbox-guest-additions/virtualbox_guest_additions-6.1.26.recipe new file mode 100644 index 000000000..28a5c48c3 --- /dev/null +++ b/app-emulation/virtualbox-guest-additions/virtualbox_guest_additions-6.1.26.recipe @@ -0,0 +1,108 @@ +SUMMARY="VirtualBox kernel modules and user-space tools for Haiku guests" +DESCRIPTION="VirtualBox is a free x86 virtualization solution allowing a wide \ +range of x86 operating systems such as Windows, DOS, BSD or Linux to run on a \ +Linux system. + +This package contains the VirtualBox kernel modules and user-space \ +tools for Haiku guests." +HOMEPAGE="https://www.virtualbox.org/" +COPYRIGHT="2003-2017 Oracle Corporation" +LICENSE=" + GNU GPL v2 + CDDL v1 + " +REVISION="1" +SOURCE_URI="http://download.virtualbox.org/virtualbox/$portVersion/VirtualBox-$portVersion.tar.bz2" +CHECKSUM_SHA256="0212602eea878d6c9fd7f4a3e0182da3e4505f31d25f5539fb8f7b1fbe366195" +SOURCE_DIR="VirtualBox-$portVersion" +PATCHES="virtualbox_guest_additions-$portVersion.patchset" + +ARCHITECTURES="!x86_gcc2 !x86 x86_64" + +PROVIDES=" + virtualbox_guest_additions$secondaryArchSuffix = $portVersion + cmd:VBoxControl$secondaryArchSuffix = $portVersion + cmd:VBoxService$secondaryArchSuffix = $portVersion + cmd:VBoxTray$secondaryArchSuffix = $portVersion + " +REQUIRES=" + haiku$secondaryArchSuffix + lib:libcurl$secondaryArchSuffix + lib:libiconv$secondaryArchSuffix + lib:libpng16$secondaryArchSuffix + lib:libz$secondaryArchSuffix + " + +BUILD_REQUIRES=" + haiku${secondaryArchSuffix}_devel + devel:libcurl$secondaryArchSuffix + devel:libiconv$secondaryArchSuffix + devel:libpng16$secondaryArchSuffix + devel:libz$secondaryArchSuffix + " +BUILD_PREREQUIRES=" + cmd:gcc$secondaryArchSuffix + cmd:grep + cmd:kmk$secondaryArchSuffix + cmd:ld$secondaryArchSuffix + cmd:mkisofs + cmd:sed + cmd:which + cmd:xres + cmd:xsltproc$secondaryArchSuffix + cmd:yasm + " + +BUILD() +{ + export USER=user + export KBUILD_PATH=`finddir B_SYSTEM_DATA_DIRECTORY`/kBuild V=1 + ./configure --only-additions + source env.sh + kmk V=1 VBOX_ONLY_ADDITIONS=1 VBOX_WITH_ADDITION_DRIVERS=1 BUILD_TYPE=strict all +} + +INSTALL() +{ + source env.sh + cd out/haiku.$BUILD_PLATFORM_ARCH/strict/bin/additions + mkdir -p $addOnsDir/kernel/{generic,drivers/bin,drivers/dev/misc} + + cp vboxguest $addOnsDir/kernel/generic + cp vboxdev $addOnsDir/kernel/drivers/bin + ln -fs ../../bin/vboxdev $addOnsDir/kernel/drivers/dev/misc + + mkdir -p $addOnsDir/kernel/file_systems + cp vboxsf $addOnsDir/kernel/file_systems + + mkdir -p $addOnsDir/{input_server/filters,input_server/devices} + cp VBoxMouseFilter $addOnsDir/input_server/filters + cp VBoxMouse $addOnsDir/input_server/devices + + mkdir -p $addOnsDir/{accelerants,kernel/drivers/dev/graphics} + cp vboxvideo $addOnsDir/kernel/drivers/bin + ln -fs ../../bin/vboxvideo $addOnsDir/kernel/drivers/dev/graphics + cp vboxvideo.accelerant $addOnsDir/accelerants + + mkdir -p $binDir + +# xres -o file.tmp VBoxControl ; strip -S VBoxControl ; xres -o VBoxControl file.tmp +# xres -o file.tmp VBoxService ; strip -S VBoxService ; xres -o VBoxService file.tmp +# xres -o file.tmp VBoxTray ; strip -S VBoxTray ; xres -o VBoxTray file.tmp + + cp VBoxControl VBoxService VBoxTray $binDir + + + # install VBoxTray replicant +# mkdir -p $prefix/boot/post-install +# cat <<'EOF' > $prefix/boot/post-install/install-VBoxTray-replicant.sh +#!/bin/sh +#/bin/VBoxTray +#EOF +# chmod a+x $prefix/boot/post-install/install-VBoxTray-replicant.sh + + + # Add a symlink to the Desktop applets directory in Deskbar + mkdir -p $dataDir/deskbar/menu/Desktop\ applets + symlinkRelative -s $binDir/VBoxTray $dataDir/deskbar/menu/Desktop\ applets +}