QosConfig.cc
Go to the documentation of this file.
1/*
2 * Copyright (C) 1996-2022 The Squid Software Foundation and contributors
3 *
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.
7 */
8
9#include "squid.h"
10#include "acl/Gadgets.h"
11#include "base/IoManip.h"
12#include "cache_cf.h"
13#include "comm/Connection.h"
14#include "compat/cmsg.h"
15#include "ConfigParser.h"
16#include "fde.h"
17#include "globals.h"
18#include "hier_code.h"
19#include "ip/QosConfig.h"
20#include "ip/tools.h"
21#include "Parsing.h"
22
23#include <cerrno>
24#include <limits>
25
27
29{
31 delete next;
32}
33
35
37{
39 delete next;
40}
41
42void
44{
45#if USE_QOS_TOS && _SQUID_LINUX_
46 /* Bug 2537: This part of ZPH only applies to patched Linux kernels. */
47 tos_t tos = 1;
48 int tos_len = sizeof(tos);
49 clientFde->tosFromServer = 0;
50 if (setsockopt(server->fd,SOL_IP,IP_RECVTOS,&tos,tos_len)==0) {
51 unsigned char buf[512];
52 int len = 512;
53 if (getsockopt(server->fd,SOL_IP,IP_PKTOPTIONS,buf,(socklen_t*)&len) == 0) {
54 /* Parse the PKTOPTIONS structure to locate the TOS data message
55 * prepared in the kernel by the ZPH incoming TCP TOS preserving
56 * patch.
57 */
58 unsigned char * pbuf = buf;
59 while (pbuf-buf < len) {
60 struct cmsghdr *o = (struct cmsghdr*)pbuf;
61 if (o->cmsg_len<=0)
62 break;
63
64 if (o->cmsg_level == SOL_IP && o->cmsg_type == IP_TOS) {
65 int *tmp = (int*)SQUID_CMSG_DATA(o);
66 clientFde->tosFromServer = (tos_t)*tmp;
67 break;
68 }
69 pbuf += CMSG_LEN(o->cmsg_len);
70 }
71 } else {
72 int xerrno = errno;
73 debugs(33, DBG_IMPORTANT, "ERROR: QOS: getsockopt(IP_PKTOPTIONS) failure on " << server << " " << xstrerr(xerrno));
74 }
75 } else {
76 int xerrno = errno;
77 debugs(33, DBG_IMPORTANT, "ERROR: QOS: setsockopt(IP_RECVTOS) failure on " << server << " " << xstrerr(xerrno));
78 }
79#else
80 (void)server;
81 (void)clientFde;
82#endif
83}
84
85#if USE_LIBNETFILTERCONNTRACK
95static int
96getNfmarkCallback(enum nf_conntrack_msg_type, struct nf_conntrack *ct, void *connmark)
97{
98 auto *mark = static_cast<nfmark_t *>(connmark);
99 *mark = nfct_get_attr_u32(ct, ATTR_MARK);
100 debugs(17, 3, asHex(*mark));
101 return NFCT_CB_CONTINUE;
102}
103
108static nf_conntrack *
109prepareConntrackQuery(const Ip::Address &src, const Ip::Address &dst)
110{
111 /* Allocate a new conntrack */
112 if (auto ct = nfct_new()) {
113 // Prepare data needed to find the connection in the conntrack table.
114 // We need the local and remote IP address, and the local and remote
115 // port numbers.
116 if (Ip::EnableIpv6 && src.isIPv6()) {
117 nfct_set_attr_u8(ct, ATTR_L3PROTO, AF_INET6);
118 struct in6_addr conn_fde_dst_ip6;
119 dst.getInAddr(conn_fde_dst_ip6);
120 nfct_set_attr(ct, ATTR_ORIG_IPV6_DST, conn_fde_dst_ip6.s6_addr);
121 struct in6_addr conn_fde_src_ip6;
122 src.getInAddr(conn_fde_src_ip6);
123 nfct_set_attr(ct, ATTR_ORIG_IPV6_SRC, conn_fde_src_ip6.s6_addr);
124 } else {
125 nfct_set_attr_u8(ct, ATTR_L3PROTO, AF_INET);
126 struct in_addr conn_fde_dst_ip;
127 dst.getInAddr(conn_fde_dst_ip);
128 nfct_set_attr_u32(ct, ATTR_ORIG_IPV4_DST, conn_fde_dst_ip.s_addr);
129 struct in_addr conn_fde_src_ip;
130 src.getInAddr(conn_fde_src_ip);
131 nfct_set_attr_u32(ct, ATTR_ORIG_IPV4_SRC, conn_fde_src_ip.s_addr);
132 }
133
134 nfct_set_attr_u8(ct, ATTR_L4PROTO, IPPROTO_TCP);
135 nfct_set_attr_u16(ct, ATTR_ORIG_PORT_DST, htons(dst.port()));
136 nfct_set_attr_u16(ct, ATTR_ORIG_PORT_SRC, htons(src.port()));
137
138 return ct;
139 }
140
141 return nullptr;
142}
143#endif
144
147{
148 nfmark_t mark = 0;
149#if USE_LIBNETFILTERCONNTRACK
150 const auto src = (connDir == Ip::Qos::dirAccepted) ? conn->remote : conn->local;
151 const auto dst = (connDir == Ip::Qos::dirAccepted) ? conn->local : conn->remote;
152
153 if (const auto ct = prepareConntrackQuery(src, dst)) {
154 // Open a handle to the conntrack
155 if (struct nfct_handle *h = nfct_open(CONNTRACK, 0)) {
156 // Register the callback. The callback function will record the mark value.
157 nfct_callback_register(h, NFCT_T_ALL, getNfmarkCallback, static_cast<void *>(&mark));
158 // Query the conntrack table using the data previously set
159 int x = nfct_query(h, NFCT_Q_GET, ct);
160 if (x == -1) {
161 const int xerrno = errno;
162 debugs(17, 2, "QOS: Failed to retrieve connection mark: (" << x << ") " << xstrerr(xerrno)
163 << " (Destination " << dst << ", source " << src << ")" );
164 }
165 nfct_close(h);
166 } else {
167 debugs(17, 2, "QOS: Failed to open conntrack handle for netfilter CONNMARK retrieval.");
168 }
169 nfct_destroy(ct);
170 } else {
171 debugs(17, 2, "QOS: Failed to allocate new conntrack for netfilter CONNMARK retrieval.");
172 }
173#else
174 (void)conn;
175 (void)connDir;
176#endif
177 return mark;
178}
179
180bool
182{
183 bool ret = false;
184
185#if USE_LIBNETFILTERCONNTRACK
186 const auto src = (connDir == Ip::Qos::dirAccepted) ? conn->remote : conn->local;
187 const auto dst = (connDir == Ip::Qos::dirAccepted) ? conn->local : conn->remote;
188
189 const nfmark_t newMark = cm.applyToMark(conn->nfConnmark);
190
191 // No need to do anything if a CONNMARK has not changed.
192 if (newMark == conn->nfConnmark)
193 return true;
194
195 if (const auto ct = prepareConntrackQuery(src, dst)) {
196 // Open a handle to the conntrack
197 if (struct nfct_handle *h = nfct_open(CONNTRACK, 0)) {
198 nfct_set_attr_u32(ct, ATTR_MARK, newMark);
199 // Update the conntrack table using the new mark. We do not need a callback here.
200 const int queryResult = nfct_query(h, NFCT_Q_UPDATE, ct);
201 if (queryResult == 0) {
202 conn->nfConnmark = newMark;
203 ret = true;
204 } else {
205 const int xerrno = errno;
206 debugs(17, 2, "QOS: Failed to modify connection mark: (" << queryResult << ") " << xstrerr(xerrno)
207 << " (Destination " << dst << ", source " << src << ")" );
208 }
209 nfct_close(h);
210 } else {
211 debugs(17, 2, "QOS: Failed to open conntrack handle for netfilter CONNMARK modification.");
212 }
213 nfct_destroy(ct);
214 } else {
215 debugs(17, 2, "QOS: Failed to allocate new conntrack for netfilter CONNMARK modification.");
216 }
217#else /* USE_LIBNETFILTERCONNTRACK */
218 (void)conn;
219 (void)connDir;
220 (void)cm;
221#endif /* USE_LIBNETFILTERCONNTRACK */
222 return ret;
223}
224
225int
227{
228 tos_t tos = 0;
229 if (Ip::Qos::TheConfig.tosSiblingHit && hierCode==SIBLING_HIT) {
231 debugs(33, 2, "QOS: Sibling Peer hit with hier code=" << hierCode << ", TOS=" << int(tos));
232 } else if (Ip::Qos::TheConfig.tosParentHit && hierCode==PARENT_HIT) {
234 debugs(33, 2, "QOS: Parent Peer hit with hier code=" << hierCode << ", TOS=" << int(tos));
235 } else if (Ip::Qos::TheConfig.preserveMissTos) {
236 tos = fd_table[conn->fd].tosFromServer & Ip::Qos::TheConfig.preserveMissTosMask;
237 tos = (tos & ~Ip::Qos::TheConfig.tosMissMask) | (Ip::Qos::TheConfig.tosMiss & Ip::Qos::TheConfig.tosMissMask);
238 debugs(33, 2, "QOS: Preserving TOS on miss, TOS=" << int(tos));
239 } else if (Ip::Qos::TheConfig.tosMiss) {
241 debugs(33, 2, "QOS: Cache miss, setting TOS=" << int(tos));
242 }
243 return setSockTos(conn, tos);
244}
245
246int
248{
249 nfmark_t mark = 0;
250 if (Ip::Qos::TheConfig.markSiblingHit && hierCode==SIBLING_HIT) {
252 debugs(33, 2, "QOS: Sibling Peer hit with hier code=" << hierCode << ", Mark=" << mark);
253 } else if (Ip::Qos::TheConfig.markParentHit && hierCode==PARENT_HIT) {
255 debugs(33, 2, "QOS: Parent Peer hit with hier code=" << hierCode << ", Mark=" << mark);
256 } else if (Ip::Qos::TheConfig.preserveMissMark) {
257 mark = fd_table[conn->fd].nfConnmarkFromServer & Ip::Qos::TheConfig.preserveMissMarkMask;
258 mark = (mark & ~Ip::Qos::TheConfig.markMissMask) | (Ip::Qos::TheConfig.markMiss & Ip::Qos::TheConfig.markMissMask);
259 debugs(33, 2, "QOS: Preserving mark on miss, Mark=" << mark);
260 } else if (Ip::Qos::TheConfig.markMiss) {
262 debugs(33, 2, "QOS: Cache miss, setting Mark=" << mark);
263 }
264 return setSockNfmark(conn, mark);
265}
266
267int
269{
270 debugs(33, 2, "QOS: Setting TOS for local hit, TOS=" << int(Ip::Qos::TheConfig.tosLocalHit));
271 return setSockTos(conn, Ip::Qos::TheConfig.tosLocalHit);
272}
273
274int
276{
277 debugs(33, 2, "QOS: Setting netfilter mark for local hit, mark=" << Ip::Qos::TheConfig.markLocalHit);
278 return setSockNfmark(conn, Ip::Qos::TheConfig.markLocalHit);
279}
280
281/* Qos::Config class */
282
284
285Ip::Qos::Config::Config() : tosLocalHit(0), tosSiblingHit(0), tosParentHit(0),
286 tosMiss(0), tosMissMask(0), preserveMissTos(false),
287 preserveMissTosMask(0xFF), markLocalHit(0), markSiblingHit(0),
288 markParentHit(0), markMiss(0), markMissMask(0),
289 preserveMissMark(false), preserveMissMarkMask(0xFFFFFFFF),
290 tosToServer(nullptr), tosToClient(nullptr), nfmarkToServer(nullptr),
291 nfmarkToClient(nullptr)
292{
293}
294
295void
297{
298 /* parse options ... */
299 char *token;
300 /* These are set as appropriate and then used to check whether the initial loop has been done */
301 bool mark = false;
302 bool tos = false;
303 /* Assume preserve is true. We don't set at initialisation as this affects isHitTosActive().
304 We have to do this now, as we may never match the 'tos' parameter below */
305#if !USE_QOS_TOS
306 debugs(3, DBG_CRITICAL, "ERROR: Invalid option 'qos_flows'. QOS features not enabled in this build");
308#endif
309
310 while ( (token = ConfigParser::NextToken()) ) {
311
312 // Work out TOS or mark. Default to TOS for backwards compatibility
313 if (!(mark || tos)) {
314 if (strncmp(token, "mark",4) == 0) {
315#if SO_MARK && USE_LIBCAP
316 mark = true;
317 // Assume preserve is true. We don't set at initialisation as this affects isHitNfmarkActive()
318#if USE_LIBNETFILTERCONNTRACK
319 preserveMissMark = true;
320# else // USE_LIBNETFILTERCONNTRACK
321 preserveMissMark = false;
322 debugs(3, DBG_IMPORTANT, "WARNING: Squid not compiled with Netfilter conntrack library. "
323 << "Netfilter mark preservation not available.");
324#endif // USE_LIBNETFILTERCONNTRACK
325#elif SO_MARK // SO_MARK && USE_LIBCAP
326 debugs(3, DBG_CRITICAL, "ERROR: Invalid parameter 'mark' in qos_flows option. "
327 << "Linux Netfilter marking not available without LIBCAP support.");
329#else // SO_MARK && USE_LIBCAP
330 debugs(3, DBG_CRITICAL, "ERROR: Invalid parameter 'mark' in qos_flows option. "
331 << "Linux Netfilter marking not available on this platform.");
333#endif // SO_MARK && USE_LIBCAP
334 } else if (strncmp(token, "tos",3) == 0) {
335 preserveMissTos = true;
336 tos = true;
337 } else {
338 preserveMissTos = true;
339 tos = true;
340 }
341 }
342
343 if (strncmp(token, "local-hit=",10) == 0) {
344
345 if (mark) {
346 if (!xstrtoui(&token[10], nullptr, &markLocalHit, 0, std::numeric_limits<nfmark_t>::max())) {
347 debugs(3, DBG_CRITICAL, "ERROR: Bad mark local-hit value " << &token[10]);
349 }
350 } else {
351 unsigned int v = 0;
352 if (!xstrtoui(&token[10], nullptr, &v, 0, std::numeric_limits<tos_t>::max())) {
353 debugs(3, DBG_CRITICAL, "ERROR: Bad TOS local-hit value " << &token[10]);
355 }
356 tosLocalHit = (tos_t)v;
357 }
358
359 } else if (strncmp(token, "sibling-hit=",12) == 0) {
360
361 if (mark) {
362 if (!xstrtoui(&token[12], nullptr, &markSiblingHit, 0, std::numeric_limits<nfmark_t>::max())) {
363 debugs(3, DBG_CRITICAL, "ERROR: Bad mark sibling-hit value " << &token[12]);
365 }
366 } else {
367 unsigned int v = 0;
368 if (!xstrtoui(&token[12], nullptr, &v, 0, std::numeric_limits<tos_t>::max())) {
369 debugs(3, DBG_CRITICAL, "ERROR: Bad TOS sibling-hit value " << &token[12]);
371 }
372 tosSiblingHit = (tos_t)v;
373 }
374
375 } else if (strncmp(token, "parent-hit=",11) == 0) {
376
377 if (mark) {
378 if (!xstrtoui(&token[11], nullptr, &markParentHit, 0, std::numeric_limits<nfmark_t>::max())) {
379 debugs(3, DBG_CRITICAL, "ERROR: Bad mark parent-hit value " << &token[11]);
381 }
382 } else {
383 unsigned int v = 0;
384 if (!xstrtoui(&token[11], nullptr, &v, 0, std::numeric_limits<tos_t>::max())) {
385 debugs(3, DBG_CRITICAL, "ERROR: Bad TOS parent-hit value " << &token[11]);
387 }
388 tosParentHit = (tos_t)v;
389 }
390
391 } else if (strncmp(token, "miss=",5) == 0) {
392
393 char *end;
394 if (mark) {
395 if (!xstrtoui(&token[5], &end, &markMiss, 0, std::numeric_limits<nfmark_t>::max())) {
396 debugs(3, DBG_CRITICAL, "ERROR: Bad mark miss value " << &token[5]);
398 }
399 if (*end == '/') {
400 if (!xstrtoui(end + 1, nullptr, &markMissMask, 0, std::numeric_limits<nfmark_t>::max())) {
401 debugs(3, DBG_CRITICAL, "ERROR: Bad mark miss mask value " << (end + 1) << ". Using 0xFFFFFFFF instead.");
402 markMissMask = 0xFFFFFFFF;
403 }
404 } else {
405 markMissMask = 0xFFFFFFFF;
406 }
407 } else {
408 unsigned int v = 0;
409 if (!xstrtoui(&token[5], &end, &v, 0, std::numeric_limits<tos_t>::max())) {
410 debugs(3, DBG_CRITICAL, "ERROR: Bad TOS miss value " << &token[5]);
412 }
413 tosMiss = (tos_t)v;
414 if (*end == '/') {
415 if (!xstrtoui(end + 1, nullptr, &v, 0, std::numeric_limits<tos_t>::max())) {
416 debugs(3, DBG_CRITICAL, "ERROR: Bad TOS miss mask value " << (end + 1) << ". Using 0xFF instead.");
417 tosMissMask = 0xFF;
418 } else
419 tosMissMask = (tos_t)v;
420 } else {
421 tosMissMask = 0xFF;
422 }
423 }
424
425 } else if (strcmp(token, "disable-preserve-miss") == 0) {
426
427 if (preserveMissTosMask!=0xFFU || preserveMissMarkMask!=0xFFFFFFFFU) {
428 debugs(3, DBG_CRITICAL, "ERROR: miss-mask feature cannot be set with disable-preserve-miss");
430 }
431 if (mark) {
432 preserveMissMark = false;
433 preserveMissMarkMask = 0;
434 } else {
435 preserveMissTos = false;
436 preserveMissTosMask = 0;
437 }
438
439 } else if (strncmp(token, "miss-mask=",10) == 0) {
440
441 if (mark && preserveMissMark) {
442 if (!xstrtoui(&token[10], nullptr, &preserveMissMarkMask, 0, std::numeric_limits<nfmark_t>::max())) {
443 debugs(3, DBG_CRITICAL, "ERROR: Bad mark miss-mark value " << &token[10]);
445 }
446 } else if (preserveMissTos) {
447 unsigned int v = 0;
448 if (!xstrtoui(&token[10], nullptr, &v, 0, std::numeric_limits<tos_t>::max())) {
449 debugs(3, DBG_CRITICAL, "ERROR: Bad TOS miss-mark value " << &token[10]);
451 }
452 preserveMissTosMask = (tos_t)v;
453 } else {
454 debugs(3, DBG_CRITICAL, "ERROR: miss-mask feature cannot be set without miss-preservation enabled");
456 }
457
458 }
459 }
460}
461
467void
468Ip::Qos::Config::dumpConfigLine(char *entry, const char *name) const
469{
470 char *p = entry;
471 if (isHitTosActive()) {
472
473 p += snprintf(p, 11, "%s", name); // strlen("qos_flows ");
474 p += snprintf(p, 4, "%s", "tos");
475
476 if (tosLocalHit > 0) {
477 p += snprintf(p, 16, " local-hit=0x%02X", tosLocalHit);
478 }
479 if (tosSiblingHit > 0) {
480 p += snprintf(p, 18, " sibling-hit=0x%02X", tosSiblingHit);
481 }
482 if (tosParentHit > 0) {
483 p += snprintf(p, 17, " parent-hit=0x%02X", tosParentHit);
484 }
485 if (tosMiss > 0) {
486 p += snprintf(p, 11, " miss=0x%02X", tosMiss);
487 if (tosMissMask!=0xFFU) {
488 p += snprintf(p, 6, "/0x%02X", tosMissMask);
489 }
490 }
491 if (preserveMissTos == 0) {
492 p += snprintf(p, 23, " disable-preserve-miss");
493 }
494 if (preserveMissTos && preserveMissTosMask != 0) {
495 p += snprintf(p, 16, " miss-mask=0x%02X", preserveMissTosMask);
496 }
497 p += snprintf(p, 2, "\n");
498 }
499
500 if (isHitNfmarkActive()) {
501 p += snprintf(p, 11, "%s", name); // strlen("qos_flows ");
502 p += snprintf(p, 5, "%s", "mark");
503
504 if (markLocalHit > 0) {
505 p += snprintf(p, 22, " local-hit=0x%02X", markLocalHit);
506 }
507 if (markSiblingHit > 0) {
508 p += snprintf(p, 24, " sibling-hit=0x%02X", markSiblingHit);
509 }
510 if (markParentHit > 0) {
511 p += snprintf(p, 23, " parent-hit=0x%02X", markParentHit);
512 }
513 if (markMiss > 0) {
514 p += snprintf(p, 17, " miss=0x%02X", markMiss);
515 if (markMissMask!=0xFFFFFFFFU) {
516 p += snprintf(p, 12, "/0x%02X", markMissMask);
517 }
518 }
519 if (preserveMissMark == false) {
520 p += snprintf(p, 23, " disable-preserve-miss");
521 }
522 if (preserveMissMark && preserveMissMarkMask != 0) {
523 p += snprintf(p, 22, " miss-mask=0x%02X", preserveMissMarkMask);
524 }
525 p += snprintf(p, 2, "\n");
526 }
527}
528
529int
530Ip::Qos::setSockTos(const int fd, tos_t tos, int type)
531{
532 // Bug 3731: FreeBSD produces 'invalid option'
533 // unless we pass it a 32-bit variable storing 8-bits of data.
534 // NP: it is documented as 'int' for all systems, even those like Linux which accept 8-bit char
535 // so we convert to a int before setting.
536 int bTos = tos;
537
538 debugs(50, 3, "for FD " << fd << " to " << bTos);
539
540 if (type == AF_INET) {
541#if defined(IP_TOS)
542 const int x = setsockopt(fd, IPPROTO_IP, IP_TOS, &bTos, sizeof(bTos));
543 if (x < 0) {
544 int xerrno = errno;
545 debugs(50, 2, "setsockopt(IP_TOS) on " << fd << ": " << xstrerr(xerrno));
546 }
547 return x;
548#else
549 debugs(50, DBG_IMPORTANT, "WARNING: setsockopt(IP_TOS) not supported on this platform");
550 return -1;
551#endif
552 } else { // type == AF_INET6
553#if defined(IPV6_TCLASS)
554 const int x = setsockopt(fd, IPPROTO_IPV6, IPV6_TCLASS, &bTos, sizeof(bTos));
555 if (x < 0) {
556 int xerrno = errno;
557 debugs(50, 2, "setsockopt(IPV6_TCLASS) on " << fd << ": " << xstrerr(xerrno));
558 }
559 return x;
560#else
561 debugs(50, DBG_IMPORTANT, "WARNING: setsockopt(IPV6_TCLASS) not supported on this platform");
562 return -1;
563#endif
564 }
565
566 /* CANNOT REACH HERE */
567}
568
569int
571{
572 const int x = Ip::Qos::setSockTos(conn->fd, tos, conn->remote.isIPv4() ? AF_INET : AF_INET6);
573 conn->tos = (x >= 0) ? tos : 0;
574 return x;
575}
576
577int
579{
580#if SO_MARK && USE_LIBCAP
581 debugs(50, 3, "for FD " << fd << " to " << mark);
582 const int x = setsockopt(fd, SOL_SOCKET, SO_MARK, &mark, sizeof(nfmark_t));
583 if (x < 0) {
584 int xerrno = errno;
585 debugs(50, 2, "setsockopt(SO_MARK) on " << fd << ": " << xstrerr(xerrno));
586 }
587 return x;
588#elif USE_LIBCAP
589 (void)mark;
590 (void)fd;
591 debugs(50, DBG_IMPORTANT, "WARNING: setsockopt(SO_MARK) not supported on this platform");
592 return -1;
593#else
594 (void)mark;
595 (void)fd;
596 debugs(50, DBG_IMPORTANT, "WARNING: Netfilter marking disabled (netfilter marking requires build with LIBCAP)");
597 return -1;
598#endif
599}
600
601int
603{
604 const int x = Ip::Qos::setSockNfmark(conn->fd, mark);
605 conn->nfmark = (x >= 0) ? mark : 0;
606 return x;
607}
608
609bool
611{
612 acl_nfmark * nfmarkAcls [] = { nfmarkToServer, nfmarkToClient };
613
614 for (int i=0; i<2; ++i) {
615 while (nfmarkAcls[i]) {
616 acl_nfmark *l = nfmarkAcls[i];
617 if (!l->markConfig.isEmpty())
618 return true;
619 nfmarkAcls[i] = l->next;
620 }
621 }
622
623 return false;
624}
625
626bool
628{
629 acl_tos * tosAcls [] = { tosToServer, tosToClient };
630
631 for (int i=0; i<2; ++i) {
632 while (tosAcls[i]) {
633 acl_tos *l = tosAcls[i];
634 if (l->tos > 0)
635 return true;
636 tosAcls[i] = l->next;
637 }
638 }
639
640 return false;
641}
642
#define false
Definition: GnuRegex.c:240
AsHex< Integer > asHex(const Integer n)
a helper to ease AsHex object creation
Definition: IoManip.h:81
CBDATA_CLASS_INIT(acl_tos)
int conn
the current server connection FD
Definition: Transport.cc:26
static char server[MAXLINE]
void self_destruct(void)
Definition: cache_cf.cc:276
static char * NextToken()
bool isIPv6() const
Definition: Address.cc:164
bool getInAddr(struct in_addr &) const
Definition: Address.cc:1020
unsigned short port() const
Definition: Address.cc:778
a netfilter mark/mask pair
Definition: NfMarkConfig.h:21
nfmark_t applyToMark(nfmark_t m) const
Definition: NfMarkConfig.cc:46
bool isEmpty() const
whether the netfilter mark is unset
Definition: NfMarkConfig.h:33
nfmark_t markParentHit
Netfilter mark value to apply to hits from parent.
Definition: QosConfig.h:224
tos_t tosMiss
TOS value to apply to cache misses.
Definition: QosConfig.h:217
bool isAclTosActive() const
Definition: QosConfig.cc:627
nfmark_t markMiss
Netfilter mark value to apply to cache misses.
Definition: QosConfig.h:225
tos_t preserveMissTosMask
The mask to apply when preserving the TOS of misses. Applies to preserved value from upstream.
Definition: QosConfig.h:220
nfmark_t markMissMask
Mask for netfilter mark value to apply to cache misses. Applied to the markMiss value.
Definition: QosConfig.h:226
nfmark_t preserveMissMarkMask
The mask to apply when preserving the netfilter mark of misses. Applied to preserved value from upstr...
Definition: QosConfig.h:228
tos_t tosMissMask
Mask for TOS value to apply to cache misses. Applied to the tosMiss value.
Definition: QosConfig.h:218
tos_t tosSiblingHit
TOS value to apply to hits from siblings.
Definition: QosConfig.h:215
void parseConfigLine()
Definition: QosConfig.cc:296
nfmark_t markSiblingHit
Netfilter mark value to apply to hits from siblings.
Definition: QosConfig.h:223
tos_t tosParentHit
TOS value to apply to hits from parent.
Definition: QosConfig.h:216
void dumpConfigLine(char *entry, const char *name) const
Definition: QosConfig.cc:468
bool isAclNfmarkActive() const
Definition: QosConfig.cc:610
acl_nfmark * next
Definition: QosConfig.h:50
Ip::NfMarkConfig markConfig
Definition: QosConfig.h:52
ACLList * aclList
Definition: QosConfig.h:51
tos_t tos
Definition: QosConfig.h:38
acl_tos * next
Definition: QosConfig.h:36
ACLList * aclList
Definition: QosConfig.h:37
~acl_tos()
Definition: QosConfig.cc:28
Definition: fde.h:52
tos_t tosFromServer
Definition: fde.h:166
#define CMSG_LEN(len)
Definition: cmsg.h:77
#define SQUID_CMSG_DATA(cmsg)
Definition: cmsg.h:51
A const & max(A const &lhs, A const &rhs)
#define DBG_IMPORTANT
Definition: Stream.h:41
#define debugs(SECTION, LEVEL, CONTENT)
Definition: Stream.h:196
#define DBG_CRITICAL
Definition: Stream.h:40
int type
Definition: errorpage.cc:152
#define fd_table
Definition: fde.h:189
void aclDestroyAclList(ACLList **list)
Definition: Gadgets.cc:270
hier_code
Definition: hier_code.h:12
@ PARENT_HIT
Definition: hier_code.h:16
@ SIBLING_HIT
Definition: hier_code.h:15
unsigned char tos_t
Definition: forward.h:27
uint32_t nfmark_t
Definition: forward.h:26
Config TheConfig
Definition: Config.cc:16
void getTosFromServer(const Comm::ConnectionPointer &server, fde *clientFde)
Definition: QosConfig.cc:43
bool setNfConnmark(Comm::ConnectionPointer &conn, const ConnectionDirection connDir, const NfMarkConfig &cm)
Definition: QosConfig.cc:181
ConnectionDirection
Possible Squid roles in connection handling.
Definition: QosConfig.h:66
@ dirAccepted
accepted (from a client by Squid)
Definition: QosConfig.h:67
int doNfmarkLocalHit(const Comm::ConnectionPointer &conn)
Definition: QosConfig.cc:275
Config TheConfig
Globally available instance of Qos::Config.
Definition: QosConfig.cc:283
int doTosLocalMiss(const Comm::ConnectionPointer &conn, const hier_code hierCode)
Definition: QosConfig.cc:226
int setSockTos(const Comm::ConnectionPointer &conn, tos_t tos)
Definition: QosConfig.cc:570
int doNfmarkLocalMiss(const Comm::ConnectionPointer &conn, const hier_code hierCode)
Definition: QosConfig.cc:247
int doTosLocalHit(const Comm::ConnectionPointer &conn)
Definition: QosConfig.cc:268
int setSockNfmark(const Comm::ConnectionPointer &conn, nfmark_t mark)
Definition: QosConfig.cc:602
nfmark_t getNfConnmark(const Comm::ConnectionPointer &conn, const ConnectionDirection connDir)
Definition: QosConfig.cc:146
Definition: client_db.h:23
int EnableIpv6
Whether IPv6 is supported and type of support.
Definition: tools.h:25
Definition: cmsg.h:35
int cmsg_type
Definition: cmsg.h:38
int cmsg_level
Definition: cmsg.h:37
unsigned int cmsg_len
Definition: cmsg.h:36
int socklen_t
Definition: types.h:158
const char * xstrerr(int error)
Definition: xstrerror.cc:83
bool xstrtoui(const char *s, char **end, unsigned int *value, unsigned int min, unsigned int max)
Definition: xstrto.cc:86

 

Introduction

Documentation

Support

Miscellaneous

Web Site Translations

Mirrors