[PATCH 2/9] handshake: Add tags to "done" downcall
Chuck Lever
cel at kernel.org
Fri Jun 5 10:34:36 PDT 2026
From: Chuck Lever <chuck.lever at oracle.com>
We'd like tlshd to tag certificates according to admin-defined
characteristics. The tag list is to be returned on a successful
handshake. Upper Layer Protocols (such as NFS) can then authorize
access based on the set of tags returned to the kernel.
For example, suppose NFSD wants to restrict access to an export to
only clients that present certificates whose issuer DN contains
"O=Oracle". tlshd can parse incoming certificates, and add an
"oraclegroup" tag to handshakes where a client presents a
certificate with "O=Oracle" somewhere in its Issuer field. NFSD can
then be configured to look for that tag and permit access only when
it is present. NFSD needs no knowledge of x.509 certificates.
This patch plumbs in the netlink protocol elements for tlshd to
return a list of tags to the kernel when a TLS or QUIC handshake
succeeds. Subsequent patches add tag extraction and storage in
the handshake layer.
Signed-off-by: Chuck Lever <chuck.lever at oracle.com>
---
Documentation/netlink/specs/handshake.yaml | 11 +++++++++++
include/uapi/linux/handshake.h | 3 +++
net/handshake/genl.c | 5 +++--
3 files changed, 17 insertions(+), 2 deletions(-)
diff --git a/Documentation/netlink/specs/handshake.yaml b/Documentation/netlink/specs/handshake.yaml
index 24f5a0ac5920..df36ff7da18f 100644
--- a/Documentation/netlink/specs/handshake.yaml
+++ b/Documentation/netlink/specs/handshake.yaml
@@ -12,6 +12,10 @@ protocol: genetlink
doc: Netlink protocol to request a transport layer security handshake.
definitions:
+ -
+ name: session-tag-max-len
+ type: const
+ value: 255
-
type: enum
name: handler-class
@@ -87,6 +91,12 @@ attribute-sets:
name: remote-auth
type: u32
multi-attr: true
+ -
+ name: tag
+ type: string
+ checks:
+ max-len: session-tag-max-len
+ multi-attr: true
operations:
list:
@@ -124,6 +134,7 @@ operations:
- status
- sockfd
- remote-auth
+ - tag
mcast-groups:
list:
diff --git a/include/uapi/linux/handshake.h b/include/uapi/linux/handshake.h
index d7e40f594888..1ed309e475b4 100644
--- a/include/uapi/linux/handshake.h
+++ b/include/uapi/linux/handshake.h
@@ -10,6 +10,8 @@
#define HANDSHAKE_FAMILY_NAME "handshake"
#define HANDSHAKE_FAMILY_VERSION 1
+#define HANDSHAKE_SESSION_TAG_MAX_LEN 255
+
enum handshake_handler_class {
HANDSHAKE_HANDLER_CLASS_NONE,
HANDSHAKE_HANDLER_CLASS_TLSHD,
@@ -56,6 +58,7 @@ enum {
HANDSHAKE_A_DONE_STATUS = 1,
HANDSHAKE_A_DONE_SOCKFD,
HANDSHAKE_A_DONE_REMOTE_AUTH,
+ HANDSHAKE_A_DONE_TAG,
__HANDSHAKE_A_DONE_MAX,
HANDSHAKE_A_DONE_MAX = (__HANDSHAKE_A_DONE_MAX - 1)
diff --git a/net/handshake/genl.c b/net/handshake/genl.c
index 791c45671cd6..385583805e02 100644
--- a/net/handshake/genl.c
+++ b/net/handshake/genl.c
@@ -17,10 +17,11 @@ static const struct nla_policy handshake_accept_nl_policy[HANDSHAKE_A_ACCEPT_HAN
};
/* HANDSHAKE_CMD_DONE - do */
-static const struct nla_policy handshake_done_nl_policy[HANDSHAKE_A_DONE_REMOTE_AUTH + 1] = {
+static const struct nla_policy handshake_done_nl_policy[HANDSHAKE_A_DONE_TAG + 1] = {
[HANDSHAKE_A_DONE_STATUS] = { .type = NLA_U32, },
[HANDSHAKE_A_DONE_SOCKFD] = { .type = NLA_S32, },
[HANDSHAKE_A_DONE_REMOTE_AUTH] = { .type = NLA_U32, },
+ [HANDSHAKE_A_DONE_TAG] = { .type = NLA_STRING, .len = HANDSHAKE_SESSION_TAG_MAX_LEN, },
};
/* Ops table for handshake */
@@ -36,7 +37,7 @@ static const struct genl_split_ops handshake_nl_ops[] = {
.cmd = HANDSHAKE_CMD_DONE,
.doit = handshake_nl_done_doit,
.policy = handshake_done_nl_policy,
- .maxattr = HANDSHAKE_A_DONE_REMOTE_AUTH,
+ .maxattr = HANDSHAKE_A_DONE_TAG,
.flags = GENL_ADMIN_PERM | GENL_CMD_CAP_DO,
},
};
--
2.54.0
More information about the Linux-nvme
mailing list