Author: sephe Date: Thu Dec 15 03:32:24 2016 New Revision: 310101 URL: https://svnweb.freebsd.org/changeset/base/310101
Log: hyperv: Allow userland to ro-mmap reference TSC page This paves way to implement VDSO for the enlightened time counter. Reviewed by: kib MFC after: 1 week Sponsored by: Microsoft Differential Revision: https://reviews.freebsd.org/D8768 Modified: head/include/Makefile head/sys/dev/hyperv/include/hyperv.h head/sys/dev/hyperv/vmbus/amd64/hyperv_machdep.c head/sys/dev/hyperv/vmbus/hyperv_reg.h Modified: head/include/Makefile ============================================================================== --- head/include/Makefile Thu Dec 15 02:05:29 2016 (r310100) +++ head/include/Makefile Thu Dec 15 03:32:24 2016 (r310101) @@ -185,6 +185,9 @@ copies: .PHONY .META ${DESTDIR}${INCLUDEDIR}/dev/evdev; \ ${INSTALL} -C -o ${BINOWN} -g ${BINGRP} -m 444 uinput.h \ ${DESTDIR}${INCLUDEDIR}/dev/evdev + cd ${.CURDIR}/../sys/dev/hyperv/include; \ + ${INSTALL} -C ${TAG_ARGS} -o ${BINOWN} -g ${BINGRP} -m 444 hyperv.h \ + ${DESTDIR}${INCLUDEDIR}/dev/hyperv cd ${.CURDIR}/../sys/dev/hyperv/utilities; \ ${INSTALL} -C ${TAG_ARGS} -o ${BINOWN} -g ${BINGRP} -m 444 hv_snapshot.h \ ${DESTDIR}${INCLUDEDIR}/dev/hyperv @@ -293,6 +296,11 @@ symlinks: .PHONY .META ln -fs ../../../../sys/dev/evdev/$$h \ ${DESTDIR}${INCLUDEDIR}/dev/evdev; \ done + cd ${.CURDIR}/../sys/dev/hyperv/include; \ + for h in hyperv.h; do \ + ${INSTALL_SYMLINK} ${TAG_ARGS} ../../../../sys/dev/hyperv/include/$$h \ + ${DESTDIR}${INCLUDEDIR}/dev/hyperv; \ + done cd ${.CURDIR}/../sys/dev/hyperv/utilities; \ for h in hv_snapshot.h; do \ ${INSTALL_SYMLINK} ${TAG_ARGS} ../../../../sys/dev/hyperv/utilities/$$h \ Modified: head/sys/dev/hyperv/include/hyperv.h ============================================================================== --- head/sys/dev/hyperv/include/hyperv.h Thu Dec 15 02:05:29 2016 (r310100) +++ head/sys/dev/hyperv/include/hyperv.h Thu Dec 15 03:32:24 2016 (r310101) @@ -31,10 +31,10 @@ #ifndef _HYPERV_H_ #define _HYPERV_H_ -#include <sys/param.h> +#ifdef _KERNEL -#include <vm/vm.h> -#include <vm/pmap.h> +#include <sys/param.h> +#include <sys/systm.h> #define MSR_HV_TIME_REF_COUNT 0x40000020 @@ -54,14 +54,35 @@ #define HYPERV_TIMER_NS_FACTOR 100ULL #define HYPERV_TIMER_FREQ (NANOSEC / HYPERV_TIMER_NS_FACTOR) +#endif /* _KERNEL */ + +#define HYPERV_REFTSC_DEVNAME "hv_tsc" + +/* + * Hyper-V Reference TSC + */ +struct hyperv_reftsc { + volatile uint32_t tsc_seq; + volatile uint32_t tsc_rsvd1; + volatile uint64_t tsc_scale; + volatile int64_t tsc_ofs; +} __packed __aligned(PAGE_SIZE); +#ifdef CTASSERT +CTASSERT(sizeof(struct hyperv_reftsc) == PAGE_SIZE); +#endif + +#ifdef _KERNEL + struct hyperv_guid { - uint8_t hv_guid[16]; + uint8_t hv_guid[16]; } __packed; -#define HYPERV_GUID_STRLEN 40 +#define HYPERV_GUID_STRLEN 40 int hyperv_guid2str(const struct hyperv_guid *, char *, size_t); extern u_int hyperv_features; /* CPUID_HV_MSR_ */ +#endif /* _KERNEL */ + #endif /* _HYPERV_H_ */ Modified: head/sys/dev/hyperv/vmbus/amd64/hyperv_machdep.c ============================================================================== --- head/sys/dev/hyperv/vmbus/amd64/hyperv_machdep.c Thu Dec 15 02:05:29 2016 (r310100) +++ head/sys/dev/hyperv/vmbus/amd64/hyperv_machdep.c Thu Dec 15 03:32:24 2016 (r310101) @@ -28,6 +28,8 @@ __FBSDID("$FreeBSD$"); #include <sys/param.h> +#include <sys/conf.h> +#include <sys/fcntl.h> #include <sys/kernel.h> #include <sys/systm.h> #include <sys/timetc.h> @@ -35,6 +37,9 @@ __FBSDID("$FreeBSD$"); #include <machine/cpufunc.h> #include <machine/cputypes.h> #include <machine/md_var.h> +#include <machine/specialreg.h> + +#include <vm/vm.h> #include <dev/hyperv/include/hyperv.h> #include <dev/hyperv/include/hyperv_busdma.h> @@ -47,6 +52,9 @@ struct hyperv_reftsc_ctx { struct hyperv_dma tsc_ref_dma; }; +static d_open_t hyperv_tsc_open; +static d_mmap_t hyperv_tsc_mmap; + static struct timecounter hyperv_tsc_timecounter = { .tc_get_timecount = NULL, /* based on CPU vendor. */ .tc_poll_pps = NULL, @@ -58,6 +66,13 @@ static struct timecounter hyperv_tsc_tim .tc_priv = NULL }; +static struct cdevsw hyperv_tsc_cdevsw = { + .d_version = D_VERSION, + .d_open = hyperv_tsc_open, + .d_mmap = hyperv_tsc_mmap, + .d_name = HYPERV_REFTSC_DEVNAME +}; + static struct hyperv_reftsc_ctx hyperv_ref_tsc; uint64_t @@ -72,6 +87,36 @@ hypercall_md(volatile void *hc_addr, uin return (status); } +static int +hyperv_tsc_open(struct cdev *dev __unused, int oflags, int devtype __unused, + struct thread *td __unused) +{ + + if (oflags & FWRITE) + return (EPERM); + return (0); +} + +static int +hyperv_tsc_mmap(struct cdev *dev __unused, vm_ooffset_t offset, + vm_paddr_t *paddr, int nprot __unused, vm_memattr_t *memattr __unused) +{ + + KASSERT(hyperv_ref_tsc.tsc_ref != NULL, ("reftsc has not been setup")); + + /* + * NOTE: + * 'nprot' does not contain information interested to us; + * WR-open is blocked by d_open. + */ + + if (offset != 0) + return (EOPNOTSUPP); + + *paddr = hyperv_ref_tsc.tsc_ref_dma.hv_paddr; + return (0); +} + #define HYPERV_TSC_TIMECOUNT(fence) \ static u_int \ hyperv_tsc_timecount_##fence(struct timecounter *tc) \ @@ -150,6 +195,10 @@ hyperv_tsc_tcinit(void *dummy __unused) /* Register "enlightened" timecounter. */ tc_init(&hyperv_tsc_timecounter); + + /* Add device for mmap(2). */ + make_dev(&hyperv_tsc_cdevsw, 0, UID_ROOT, GID_WHEEL, 0444, + HYPERV_REFTSC_DEVNAME); } SYSINIT(hyperv_tsc_init, SI_SUB_DRIVERS, SI_ORDER_FIRST, hyperv_tsc_tcinit, NULL); Modified: head/sys/dev/hyperv/vmbus/hyperv_reg.h ============================================================================== --- head/sys/dev/hyperv/vmbus/hyperv_reg.h Thu Dec 15 02:05:29 2016 (r310100) +++ head/sys/dev/hyperv/vmbus/hyperv_reg.h Thu Dec 15 03:32:24 2016 (r310101) @@ -129,17 +129,6 @@ #define CPUID_LEAF_HV_HWFEATURES 0x40000006 /* - * Hyper-V Reference TSC - */ -struct hyperv_reftsc { - volatile uint32_t tsc_seq; - volatile uint32_t tsc_rsvd1; - volatile uint64_t tsc_scale; - volatile int64_t tsc_ofs; -} __packed __aligned(PAGE_SIZE); -CTASSERT(sizeof(struct hyperv_reftsc) == PAGE_SIZE); - -/* * Hyper-V Monitor Notification Facility */ struct hyperv_mon_param { _______________________________________________ svn-src-head@freebsd.org mailing list https://lists.freebsd.org/mailman/listinfo/svn-src-head To unsubscribe, send any mail to "svn-src-head-unsubscr...@freebsd.org"