C++ Logo

liaison

Advanced search

[wg14/wg21 liaison] Fwd: native_handle_type

From: Niall Douglas <s_sourceforge_at_[hidden]>
Date: Mon, 19 Aug 2019 14:43:22 +0100
Looping in WG21/WG14 liaison.


-------- Forwarded Message --------
Subject: native_handle_type
Date: Mon, 19 Aug 2019 14:42:18 +0100
From: Niall Douglas <s_sourceforge_at_[hidden]>
To: ISO C <sc22wg14_at_[hidden]>

Dear WG14,

WG21 is thinking about standardising a native_handle_type, which is a
one-one typedef to whatever is your native handle type on your platform.

I find severe issue with that, as platforms can have more than one
native handle type e.g. Microsoft Windows, where SOCKET, HANDLE and
`int` come to mind (there are in fact many more).

It is also not C-compatible, for zero good reason, when one of its
motivating reasons is to extract a file descriptor from a FILE *. You
can see the latest paper at
http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2019/p1759r1.html.


I discussed this briefly with some WG14 members in person, but I was
wondering what the list thinks about this alternative C-compatible design:

struct native_handle_type
{
  union
  {
#ifdef _WIN32
    SOCKET socket_value;
    HANDLE handle_value;
#endif
    FILE *fileptr_value;
    int fd_value;
  };

  // disposition bits which cache information about the handle
  // http://pubs.opengroup.org/onlinepubs/7908799/xsh/sysstat.h.html
  // e.g. readable, is_directory, etc
  // but also a few extra e.g. is_direct_io (O_DIRECT)
  // POSIX mode_t is a totally valid choice here

  /*unspecified*/ disposition;
};

/* Generic macro retrieving the native handle type for some input type
*/
#define get_native_handle_type(...)

// Query macros
#define NATIVE_HANDLE_TYPE_ISVALID(x)
...

// Query macros matching POSIX S_IS*()
#define NATIVE_HANDLE_TYPE_ISDIR(x)
...


Example of use in C:

FILE *h = fopen("foo", "wt");
struct native_handle_type nht = get_native_handle_type(h);
printf("The native handle type is a directory = %d\n",
NATIVE_HANDLE_TYPE_ISDIR(nht));

Example of use in C++:

std::ofstream h("foo");

struct native_handle_type nht = get_native_handle_type(h);
assert(NATIVE_HANDLE_TYPE_ISFILEPTR(nht));
printf("The native handle for std::ofstream is FILE * %p\n",
nht.fileptr_value);

struct native_handle_type nht2 = get_native_handle_type(nht.fileptr_value);
assert(NATIVE_HANDLE_TYPE_ISREGULAR(nht2));
printf("The native handle for std::ofstream's underlying FILE * is int
%d\n", nht2.fd_value);



If WG14 does not oppose this proposed design in principle, I'm minded to
propose this alternative union-based native handle type to WG21 to try
and nip in the bud their present intended design. I would intend it to
be C-compatible, as C code does also sometimes need to ask FILE* for its
native handle.

Preferred WG14 naming for the above is, of course, welcome.

Niall

Received on 2019-08-19 08:45:27