- From 4adb0047011adf9d7baa987a2920f2152b0196f5 Mon Sep 17 00:00:00 2001
- From: Roland Mainz <roland.mainz@nrubsig.org>
- Date: Sat, 1 Jun 2024 12:42:29 +0200
- Subject: [PATCH 1/4] daemon: Use |GetTickCount64()| for cache expiration
- Switch over cache expiration calculations from |time()| to
- |GetTickCount64()|, as it is almost twice as fast.
- Signed-off-by: Cedric Blancher <cedric.blancher@gmail.com>
- ---
- daemon/idmap.c | 17 ++++++++---------
- daemon/name_cache.c | 13 ++++++-------
- daemon/sid.c | 14 +++++++-------
- daemon/util.h | 14 ++++++++++++++
- 4 files changed, 35 insertions(+), 23 deletions(-)
- diff --git a/daemon/idmap.c b/daemon/idmap.c
- index 5745b7a..d7bf794 100644
- --- a/daemon/idmap.c
- +++ b/daemon/idmap.c
- @@ -25,7 +25,6 @@
- #include <Winldap.h>
- #include <stdlib.h> /* for strtoul() */
- #include <errno.h>
- -#include <time.h>
- #include "nfs41_build_features.h"
- #include "idmap.h"
- @@ -481,7 +480,7 @@ struct idmap_user {
- char principal[VAL_LEN];
- uid_t uid;
- gid_t gid;
- - time_t last_updated;
- + util_reltimestamp last_updated;
- };
- static struct list_entry* user_cache_alloc()
- @@ -517,7 +516,7 @@ struct idmap_group {
- struct list_entry entry;
- char name[VAL_LEN];
- gid_t gid;
- - time_t last_updated;
- + util_reltimestamp last_updated;
- };
- static struct list_entry* group_cache_alloc()
- @@ -676,7 +675,7 @@ static int idmap_lookup_user(
- if (status == NO_ERROR) {
- /* don't return expired entries; query new attributes
- * and overwrite the entry with cache_insert() */
- - if (difftime(time(NULL), user->last_updated) < (double)context->config.cache_ttl)
- + if (UTIL_DIFFRELTIME(UTIL_GETRELTIME(), user->last_updated) < context->config.cache_ttl)
- goto out;
- }
- #ifndef NFS41_DRIVER_FEATURE_IDMAPPER_CYGWIN
- @@ -715,7 +714,7 @@ static int idmap_lookup_user(
- status = ERROR_INVALID_PARAMETER;
- goto out_free_values;
- }
- - user->last_updated = time(NULL);
- + user->last_updated = UTIL_GETRELTIME();
- #else
- if (lookup->attr == ATTR_USER_NAME) {
- char principal_name[VAL_LEN];
- @@ -801,7 +800,7 @@ static int idmap_lookup_user(
- }
- if (status == 0) {
- - user->last_updated = time(NULL);
- + user->last_updated = UTIL_GETRELTIME();
- DPRINTF(CYGWINIDLVL, ("## idmap_lookup_user: "
- "found username='%s', principal='%s', uid=%u, gid=%u\n",
- user->username,
- @@ -840,7 +839,7 @@ static int idmap_lookup_group(
- if (status == NO_ERROR) {
- /* don't return expired entries; query new attributes
- * and overwrite the entry with cache_insert() */
- - if (difftime(time(NULL), group->last_updated) < (double)context->config.cache_ttl)
- + if (UTIL_DIFFRELTIME(UTIL_GETRELTIME(), group->last_updated) < context->config.cache_ttl)
- goto out;
- }
- #ifndef NFS41_DRIVER_FEATURE_IDMAPPER_CYGWIN
- @@ -865,7 +864,7 @@ static int idmap_lookup_group(
- status = ERROR_INVALID_PARAMETER;
- goto out_free_values;
- }
- - group->last_updated = time(NULL);
- + group->last_updated = UTIL_GETRELTIME();
- #else
- if (lookup->attr == ATTR_GROUP_NAME) {
- gid_t cy_gid = 0;
- @@ -908,7 +907,7 @@ static int idmap_lookup_group(
- }
- if (status == 0) {
- - group->last_updated = time(NULL);
- + group->last_updated = UTIL_GETRELTIME();
- DPRINTF(CYGWINIDLVL,
- ("## idmap_lookup_group: found name='%s', gid=%u\n",
- group->name,
- diff --git a/daemon/name_cache.c b/daemon/name_cache.c
- index f082edb..aa77d57 100644
- --- a/daemon/name_cache.c
- +++ b/daemon/name_cache.c
- @@ -75,7 +75,6 @@ static __inline bool_t is_delegation(
- return type == OPEN_DELEGATE_READ || type == OPEN_DELEGATE_WRITE;
- }
- -
- /* attribute cache */
- struct attr_cache_entry {
- RB_ENTRY(attr_cache_entry) rbnode;
- @@ -94,7 +93,7 @@ struct attr_cache_entry {
- unsigned hidden : 1;
- unsigned system : 1;
- unsigned archive : 1;
- - time_t expiration;
- + util_reltimestamp expiration;
- unsigned ref_count : 26;
- unsigned type : 4;
- unsigned invalidated : 1;
- @@ -181,7 +180,7 @@ static __inline int attr_cache_entry_expired(
- IN const struct attr_cache_entry *entry)
- {
- return entry->invalidated ||
- - (!entry->delegated && time(NULL) > entry->expiration);
- + ((!entry->delegated) && (UTIL_GETRELTIME() > entry->expiration));
- }
- /* attr_cache */
- @@ -294,7 +293,7 @@ static void attr_cache_update(
- entry->change = info->change;
- /* revalidate whenever we get a change attribute */
- entry->invalidated = 0;
- - entry->expiration = time(NULL) + NAME_CACHE_EXPIRATION;
- + entry->expiration = UTIL_GETRELTIME() + NAME_CACHE_EXPIRATION;
- }
- if (info->attrmask.arr[0] & FATTR4_WORD0_SIZE)
- entry->size = info->size;
- @@ -408,7 +407,7 @@ struct name_cache_entry {
- struct attr_cache_entry *attributes;
- struct name_cache_entry *parent;
- struct list_entry exp_entry;
- - time_t expiration;
- + util_reltimestamp expiration;
- unsigned short component_len;
- };
- #define NAME_ENTRY_SIZE sizeof(struct name_cache_entry)
- @@ -553,7 +552,7 @@ static void name_cache_entry_updated(
- IN struct name_cache_entry *entry)
- {
- /* update the expiration timer */
- - entry->expiration = time(NULL) + cache->expiration;
- + entry->expiration = UTIL_GETRELTIME() + cache->expiration;
- name_cache_entry_accessed(cache, entry);
- }
- @@ -669,7 +668,7 @@ static int entry_invis(
- OUT OPTIONAL bool_t *is_negative)
- {
- /* name entry timer expired? */
- - if (!list_empty(&entry->exp_entry) && time(NULL) > entry->expiration) {
- + if (!list_empty(&entry->exp_entry) && (UTIL_GETRELTIME() > entry->expiration)) {
- DPRINTF(NCLVL2, ("name_entry_expired('%s')\n", entry->component));
- return 1;
- }
- diff --git a/daemon/sid.c b/daemon/sid.c
- index c0a04cc..2a63763 100644
- --- a/daemon/sid.c
- +++ b/daemon/sid.c
- @@ -233,7 +233,7 @@ typedef struct _sidcache_entry
- #pragma warning (disable : 4324)
- DECLARE_SID_BUFFER(sid_buffer);
- #pragma warning( pop )
- - time_t timestamp;
- + util_reltimestamp timestamp;
- } sidcache_entry;
- typedef struct _sidcache
- @@ -259,12 +259,12 @@ void sidcache_add(sidcache *cache, const char* win32name, PSID value)
- {
- int i;
- ssize_t freeEntryIndex;
- - time_t currentTimestamp;
- + util_reltimestamp currentTimestamp;
- EASSERT(win32name[0] != '\0');
- EnterCriticalSection(&cache->lock);
- - currentTimestamp = time(NULL);
- + currentTimestamp = UTIL_GETRELTIME();
- /* purge obsolete entries */
- for (i = 0; i < SIDCACHE_SIZE; i++) {
- @@ -326,12 +326,12 @@ done:
- PSID *sidcache_getcached_byname(sidcache *cache, const char *win32name)
- {
- int i;
- - time_t currentTimestamp;
- + util_reltimestamp currentTimestamp;
- sidcache_entry *e;
- PSID *ret_sid = NULL;
- EnterCriticalSection(&cache->lock);
- - currentTimestamp = time(NULL);
- + currentTimestamp = UTIL_GETRELTIME();
- for (i = 0; i < SIDCACHE_SIZE; i++) {
- e = &cache->entries[i];
- @@ -361,12 +361,12 @@ done:
- bool sidcache_getcached_bysid(sidcache *cache, PSID sid, char *out_win32name)
- {
- int i;
- - time_t currentTimestamp;
- + util_reltimestamp currentTimestamp;
- sidcache_entry *e;
- bool ret = false;
- EnterCriticalSection(&cache->lock);
- - currentTimestamp = time(NULL);
- + currentTimestamp = UTIL_GETRELTIME();
- for (i = 0; i < SIDCACHE_SIZE; i++) {
- e = &cache->entries[i];
- diff --git a/daemon/util.h b/daemon/util.h
- index 99e2dd9..e350cf8 100644
- --- a/daemon/util.h
- +++ b/daemon/util.h
- @@ -34,6 +34,20 @@ struct __nfs41_session;
- struct __nfs41_write_verf;
- enum stable_how4;
- +/*
- + * UTIL_GETRELTIME - Get a relative time stamp
- + * |GetTickCount64()| is almost twice as fast as |time()|, and
- + * cache code only needs a relative timestamp and not the
- + * absolute time to implement cache element expiration.
- + * |GetTickCount64()| also includes time spend in hibernation&co.,
- + * so hibernation longer than |NAME_CACHE_EXPIRATION| will
- + * automagically invalidate the cache
- + */
- +#define UTIL_GETRELTIME() (GetTickCount64()/1000UL)
- +#define UTIL_DIFFRELTIME(t1, t2) \
- + (((signed long long)(t1))-((signed long long)(t2)))
- +typedef ULONGLONG util_reltimestamp;
- +
- /*
- * LargeInteger.QuadPart value to indicate a time value was not
- * available
- --
- 2.43.0
- From 217f69a917799a5c0fbe959388f71c8901b37cae Mon Sep 17 00:00:00 2001
- From: Roland Mainz <roland.mainz@nrubsig.org>
- Date: Sat, 1 Jun 2024 13:05:47 +0200
- Subject: [PATCH 2/4] sys: Add debug output to |nfs41_Flush()|
- Add debug output to |nfs41_Flush()|
- Signed-off-by: Cedric Blancher <cedric.blancher@gmail.com>
- ---
- sys/nfs41_driver.c | 3 +++
- 1 file changed, 3 insertions(+)
- diff --git a/sys/nfs41_driver.c b/sys/nfs41_driver.c
- index 729eb25..fa347d4 100644
- --- a/sys/nfs41_driver.c
- +++ b/sys/nfs41_driver.c
- @@ -4412,6 +4412,9 @@ out:
- NTSTATUS nfs41_Flush(
- IN OUT PRX_CONTEXT RxContext)
- {
- + DbgP("nfs41_Flush: FileName='%wZ'\n",
- + GET_ALREADY_PREFIXED_NAME_FROM_CONTEXT(RxContext));
- +
- return STATUS_SUCCESS;
- }
- --
- 2.43.0
- From 3bf222ee6c799108e3ef62138eba627c143bddac Mon Sep 17 00:00:00 2001
- From: Roland Mainz <roland.mainz@nrubsig.org>
- Date: Sat, 1 Jun 2024 13:26:24 +0200
- Subject: [PATCH 3/4] sys: nfs_mount should return |ERROR_ACCESS_DENIED| for
- NFSv4 |EPERM|
- nfs_mount.exe returns |ERROR_NO_SYSTEM_RESOURCES|(=1450) for NFSv4
- |EPERM| instead of the |expected ERROR_ACCESS_DENIED|(=5).
- Encountered while trying to mount a NFSv4.1 share through NAT
- when the server didn't export that filesystem with the "insecure"
- export option.
- Fix is to map |ERROR_ACCESS_DENIED| (returned by nfsd.exe)
- in nfs41_driver.sys's |map_mount_errors()| to
- |STATUS_ACCESS_DENIED|, which Win32 will then turn into
- |ERROR_ACCESS_DENIED| again.
- Reported-by: Josh Hurst <joshhurst@gmail.com>
- Signed-off-by: Cedric Blancher <cedric.blancher@gmail.com>
- ---
- sys/nfs41_driver.c | 1 +
- 1 file changed, 1 insertion(+)
- diff --git a/sys/nfs41_driver.c b/sys/nfs41_driver.c
- index fa347d4..2f4b912 100644
- --- a/sys/nfs41_driver.c
- +++ b/sys/nfs41_driver.c
- @@ -2757,6 +2757,7 @@ NTSTATUS map_mount_errors(
- {
- switch (status) {
- case NO_ERROR: return STATUS_SUCCESS;
- + case ERROR_ACCESS_DENIED: return STATUS_ACCESS_DENIED;
- case ERROR_NETWORK_UNREACHABLE: return STATUS_NETWORK_UNREACHABLE;
- case ERROR_BAD_NET_RESP: return STATUS_UNEXPECTED_NETWORK_ERROR;
- case ERROR_BAD_NET_NAME: return STATUS_BAD_NETWORK_NAME;
- --
- 2.43.0
- From fd18f1aa0a64b4f4b512b57c77fd923b420a8a7d Mon Sep 17 00:00:00 2001
- From: Roland Mainz <roland.mainz@nrubsig.org>
- Date: Sat, 1 Jun 2024 15:47:53 +0200
- Subject: [PATCH 4/4] sys: |nfs41_fcb->...EndOfFile| should always <=
- |nfs41_fcb->...AllocationSize|
- |nfs41_fcb->StandardInfo.EndOfFile.QuadPart| should always be smaller
- or equal to |nfs41_fcb->StandardInfo.AllocationSize|
- Signed-off-by: Cedric Blancher <cedric.blancher@gmail.com>
- ---
- sys/nfs41_driver.c | 27 ++++++++++++++++++---------
- 1 file changed, 18 insertions(+), 9 deletions(-)
- diff --git a/sys/nfs41_driver.c b/sys/nfs41_driver.c
- index 2f4b912..b82de23 100644
- --- a/sys/nfs41_driver.c
- +++ b/sys/nfs41_driver.c
- @@ -5942,19 +5942,28 @@ NTSTATUS nfs41_SetFileInformation(
- goto out;
- }
- case FileAllocationInformation:
- - /*
- - * Fixme: What is the correct way to handle
- - * |FileAllocationInformation| ? NFSv4 does not have the
- - * concept of a difference between "allocation size" and
- - * "end-of-file" position
- - */
- - break;
- + {
- + PFILE_ALLOCATION_INFORMATION info =
- + (PFILE_ALLOCATION_INFORMATION)RxContext->Info.Buffer;
- +
- + nfs41_fcb->StandardInfo.AllocationSize.QuadPart = info->AllocationSize.QuadPart;
- + if (nfs41_fcb->StandardInfo.EndOfFile.QuadPart > info->AllocationSize.QuadPart) {
- + nfs41_fcb->StandardInfo.EndOfFile.QuadPart = info->AllocationSize.QuadPart;
- + }
- + break;
- + }
- case FileEndOfFileInformation:
- {
- PFILE_END_OF_FILE_INFORMATION info =
- (PFILE_END_OF_FILE_INFORMATION)RxContext->Info.Buffer;
- - nfs41_fcb->StandardInfo.AllocationSize =
- - nfs41_fcb->StandardInfo.EndOfFile = info->EndOfFile;
- +
- + if (info->EndOfFile.QuadPart > nfs41_fcb->StandardInfo.AllocationSize.QuadPart) {
- + nfs41_fcb->StandardInfo.AllocationSize.QuadPart =
- + nfs41_fcb->StandardInfo.EndOfFile.QuadPart = info->EndOfFile.QuadPart;
- + }
- + else {
- + nfs41_fcb->StandardInfo.EndOfFile.QuadPart = info->EndOfFile.QuadPart;
- + }
- break;
- }
- case FileRenameInformation:
- --
- 2.43.0
msnfs41client: Patches for UseGetTickCount64() for caches, nfs_mount EPERM propagation, allocationsize-vs-eofpos+misc, 2024-06-01
Posted by Anonymous on Sat 1st Jun 2024 15:10
raw | new post
Submit a correction or amendment below (click here to make a fresh posting)
After submitting an amendment, you'll be able to view the differences between the old and new posts easily.