9pfs: improve v9fs_open() tracing

Improve tracing of 9p 'Topen' request type by showing open() flags as
human-readable text.

E.g. trace output:

  v9fs_open tag 0 id 12 fid 2 mode 100352

would become:

  v9fs_open tag=0 id=12 fid=2 mode=100352(RDONLY|NONBLOCK|DIRECTORY|
  TMPFILE|NDELAY)

Therefor add a new utility function qemu_open_flags_tostr() that converts
numeric open() flags from host's native O_* flag constants to a string
presentation.

9p2000.L and 9p2000.u protocol variants use different numeric 'mode'
constants for 'Topen' requests. Instead of writing string conversion code
for both protocol variants, use the already existing conversion functions
that convert the mode flags from respective protocol constants to host's
native open() numeric flag constants and pass that result to the new
string conversion function qemu_open_flags_tostr().

Signed-off-by: Christian Schoenebeck <qemu_oss@crudebyte.com>
Message-Id: <E1tTgDR-000oRr-9g@kylie.crudebyte.com>
This commit is contained in:
Christian Schoenebeck 2025-01-03 12:33:40 +01:00
parent a2f17bd40b
commit 9a0dd4b3e4
5 changed files with 66 additions and 2 deletions

50
hw/9pfs/9p-util-generic.c Normal file
View file

@ -0,0 +1,50 @@
/* SPDX-License-Identifier: GPL-2.0-or-later */
#include "qemu/osdep.h"
#include "9p-util.h"
#include <glib/gstrfuncs.h>
char *qemu_open_flags_tostr(int flags)
{
int acc = flags & O_ACCMODE;
return g_strconcat(
(acc == O_WRONLY) ? "WRONLY" : (acc == O_RDONLY) ? "RDONLY" : "RDWR",
(flags & O_CREAT) ? "|CREAT" : "",
(flags & O_EXCL) ? "|EXCL" : "",
(flags & O_NOCTTY) ? "|NOCTTY" : "",
(flags & O_TRUNC) ? "|TRUNC" : "",
(flags & O_APPEND) ? "|APPEND" : "",
(flags & O_NONBLOCK) ? "|NONBLOCK" : "",
(flags & O_DSYNC) ? "|DSYNC" : "",
#ifdef O_DIRECT
(flags & O_DIRECT) ? "|DIRECT" : "",
#endif
(flags & O_LARGEFILE) ? "|LARGEFILE" : "",
(flags & O_DIRECTORY) ? "|DIRECTORY" : "",
(flags & O_NOFOLLOW) ? "|NOFOLLOW" : "",
#ifdef O_NOATIME
(flags & O_NOATIME) ? "|NOATIME" : "",
#endif
#ifdef O_CLOEXEC
(flags & O_CLOEXEC) ? "|CLOEXEC" : "",
#endif
#ifdef __O_SYNC
(flags & __O_SYNC) ? "|SYNC" : "",
#else
((flags & O_SYNC) == O_SYNC) ? "|SYNC" : "",
#endif
#ifdef O_PATH
(flags & O_PATH) ? "|PATH" : "",
#endif
#ifdef __O_TMPFILE
(flags & __O_TMPFILE) ? "|TMPFILE" : "",
#elif defined(O_TMPFILE)
((flags & O_TMPFILE) == O_TMPFILE) ? "|TMPFILE" : "",
#endif
/* O_NDELAY is usually just an alias of O_NONBLOCK */
#if defined(O_NDELAY) && O_NDELAY != O_NONBLOCK
(flags & O_NDELAY) ? "|NDELAY" : "",
#endif
NULL /* always last (required NULL termination) */
);
}