]> git.ipfire.org Git - thirdparty/squid.git/blame - src/ipc/TypedMsgHdr.h
CI: Upgrade GitHub Setup Node and CodeQL actions to Node 20 (#1845)
[thirdparty/squid.git] / src / ipc / TypedMsgHdr.h
CommitLineData
98d9bd29 1/*
b8ae064d 2 * Copyright (C) 1996-2023 The Squid Software Foundation and contributors
98d9bd29 3 *
bbc27441
AJ
4 * Squid software is distributed under GPLv2+ license and includes
5 * contributions from numerous individuals and organizations.
6 * Please see the COPYING and CONTRIBUTORS files for details.
98d9bd29
AR
7 */
8
bbc27441
AJ
9/* DEBUG: section 54 Interprocess Communication */
10
ff9d9458
FC
11#ifndef SQUID_SRC_IPC_TYPEDMSGHDR_H
12#define SQUID_SRC_IPC_TYPEDMSGHDR_H
98d9bd29 13
5a7908bb 14#include "compat/cmsg.h"
6ccfd70a 15#include "ipc/Messages.h"
9614899c 16#if HAVE_SYS_SOCKET_H
98d9bd29 17#include <sys/socket.h>
9614899c
AJ
18#endif
19#if HAVE_SYS_UIO_H
20#include <sys/uio.h>
21#endif
98d9bd29
AR
22#if HAVE_SYS_UN_H
23#include <sys/un.h>
24#endif
25
8c0dc3d4
AR
26#include <type_traits>
27
8822ebee
AR
28class String;
29
98d9bd29
AR
30namespace Ipc
31{
32
33/// struct msghdr with a known type, fixed-size I/O and control buffers
34class TypedMsgHdr: public msghdr
35{
8822ebee
AR
36public:
37 enum {maxSize = 4096};
38
98d9bd29
AR
39public:
40 TypedMsgHdr();
41 TypedMsgHdr(const TypedMsgHdr &tmh);
42 TypedMsgHdr &operator =(const TypedMsgHdr &tmh);
43
8822ebee
AR
44 void address(const struct sockaddr_un &addr); ///< sets [dest.] address
45
46 /* message type manipulation; these must be called before put/get*() */
47 void setType(int aType); ///< sets message type; use MessageType enum
48 void checkType(int aType) const; ///< throws if stored type is not aType
6ccfd70a
EB
49 /// received or set message kind; may not be a MessageType value
50 /// \returns 0 if no message kind has been received or set
51 int rawType() const { return msg_iov ? data.type_ : 0; }
8822ebee 52
4c218615
EB
53 /* access for TriviallyCopyable (a.k.a. Plain Old Data or POD) message parts */
54 template <class Pod> void getPod(Pod &pod) const; ///< load POD
55 template <class Pod> void putPod(const Pod &pod); ///< store POD
8822ebee
AR
56
57 /* access to message parts for selected commonly-used part types */
58 void getString(String &s) const; ///< load variable-length string
59 void putString(const String &s); ///< store variable-length string
60 int getInt() const; ///< load an integer
61 void putInt(int n); ///< store an integer
62 void getFixed(void *raw, size_t size) const; ///< always load size bytes
63 void putFixed(const void *raw, size_t size); ///< always store size bytes
64
65 /// returns true if there is data to extract; handy for optional parts
66 bool hasMoreData() const { return offset < data.size; }
67
68 /* access to a "file" descriptor that can be passed between processes */
5667a628 69 void putFd(int aFd); ///< stores descriptor
9b440559
CT
70 int getFd() const; ///< returns stored descriptor
71 bool hasFd() const; ///< whether the message has a descriptor stored
98d9bd29 72
8822ebee 73 /* raw, type-independent access for I/O */
5667a628
AR
74 void prepForReading(); ///< reset and provide all buffers
75 char *raw() { return reinterpret_cast<char*>(this); }
76 const char *raw() const { return reinterpret_cast<const char*>(this); }
98d9bd29
AR
77 size_t size() const { return sizeof(*this); } ///< not true message size
78
79private:
b56b37cf 80 void clear();
5667a628
AR
81 void sync();
82 void allocData();
83 void allocName();
84 void allocControl();
98d9bd29 85
8822ebee
AR
86 /* raw, type-independent manipulation used by type-specific methods */
87 void getRaw(void *raw, size_t size) const;
88 void putRaw(const void *raw, size_t size);
89
98d9bd29 90private:
5667a628 91 struct sockaddr_un name; ///< same as .msg_name
98d9bd29 92
5667a628 93 struct iovec ios[1]; ///< same as .msg_iov[]
98d9bd29 94
5667a628 95 struct DataBuffer {
b56b37cf
AJ
96 DataBuffer() { memset(raw, 0, sizeof(raw)); }
97
98 int type_ = 0; ///< Message kind, uses MessageType values
99 size_t size = 0; ///< actual raw data size (for sanity checks)
8822ebee 100 char raw[maxSize]; ///< buffer with type-specific data
5667a628 101 } data; ///< same as .msg_iov[0].iov_base
98d9bd29 102
5667a628 103 struct CtrlBuffer {
b56b37cf
AJ
104 CtrlBuffer() { memset(raw, 0, sizeof(raw)); }
105
14c0d3ab
DK
106 /// control buffer space for one fd
107 char raw[SQUID_CMSG_SPACE(sizeof(int))];
5667a628 108 } ctrl; ///< same as .msg_control
8822ebee
AR
109
110 /// data offset for the next get/put*() to start with
b56b37cf 111 mutable unsigned int offset = 0;
98d9bd29
AR
112};
113
114} // namespace Ipc
115
4c218615
EB
116template <class Pod>
117void
118Ipc::TypedMsgHdr::getPod(Pod &pod) const
119{
8c0dc3d4 120 static_assert(std::is_trivially_copyable<Pod>::value, "getPod() used for a POD");
4c218615
EB
121 getFixed(&pod, sizeof(pod));
122}
123
124template <class Pod>
125void
126Ipc::TypedMsgHdr::putPod(const Pod &pod)
127{
8c0dc3d4 128 static_assert(std::is_trivially_copyable<Pod>::value, "putPod() used for a POD");
4c218615
EB
129 putFixed(&pod, sizeof(pod));
130}
131
ff9d9458 132#endif /* SQUID_SRC_IPC_TYPEDMSGHDR_H */
f53969cc 133