PostgreSQL Source Code  git master
network.c File Reference
#include "postgres.h"
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include "access/stratnum.h"
#include "catalog/pg_opfamily.h"
#include "catalog/pg_type.h"
#include "common/hashfn.h"
#include "common/ip.h"
#include "lib/hyperloglog.h"
#include "libpq/libpq-be.h"
#include "libpq/pqformat.h"
#include "miscadmin.h"
#include "nodes/makefuncs.h"
#include "nodes/nodeFuncs.h"
#include "nodes/supportnodes.h"
#include "utils/builtins.h"
#include "utils/fmgroids.h"
#include "utils/guc.h"
#include "utils/inet.h"
#include "utils/lsyscache.h"
#include "utils/sortsupport.h"
Include dependency graph for network.c:

Go to the source code of this file.

Data Structures

struct  network_sortsupport_state
 

Macros

#define ABBREV_BITS_INET4_NETMASK_SIZE   6
 
#define ABBREV_BITS_INET4_SUBNET   25
 

Functions

static int32 network_cmp_internal (inet *a1, inet *a2)
 
static int network_fast_cmp (Datum x, Datum y, SortSupport ssup)
 
static bool network_abbrev_abort (int memtupcount, SortSupport ssup)
 
static Datum network_abbrev_convert (Datum original, SortSupport ssup)
 
static Listmatch_network_function (Node *leftop, Node *rightop, int indexarg, Oid funcid, Oid opfamily)
 
static Listmatch_network_subset (Node *leftop, Node *rightop, bool is_eq, Oid opfamily)
 
static bool addressOK (unsigned char *a, int bits, int family)
 
static inetinternal_inetpl (inet *ip, int64 addend)
 
static inetnetwork_in (char *src, bool is_cidr, Node *escontext)
 
Datum inet_in (PG_FUNCTION_ARGS)
 
Datum cidr_in (PG_FUNCTION_ARGS)
 
static char * network_out (inet *src, bool is_cidr)
 
Datum inet_out (PG_FUNCTION_ARGS)
 
Datum cidr_out (PG_FUNCTION_ARGS)
 
static inetnetwork_recv (StringInfo buf, bool is_cidr)
 
Datum inet_recv (PG_FUNCTION_ARGS)
 
Datum cidr_recv (PG_FUNCTION_ARGS)
 
static byteanetwork_send (inet *addr, bool is_cidr)
 
Datum inet_send (PG_FUNCTION_ARGS)
 
Datum cidr_send (PG_FUNCTION_ARGS)
 
Datum inet_to_cidr (PG_FUNCTION_ARGS)
 
Datum inet_set_masklen (PG_FUNCTION_ARGS)
 
Datum cidr_set_masklen (PG_FUNCTION_ARGS)
 
inetcidr_set_masklen_internal (const inet *src, int bits)
 
Datum network_cmp (PG_FUNCTION_ARGS)
 
Datum network_sortsupport (PG_FUNCTION_ARGS)
 
Datum network_lt (PG_FUNCTION_ARGS)
 
Datum network_le (PG_FUNCTION_ARGS)
 
Datum network_eq (PG_FUNCTION_ARGS)
 
Datum network_ge (PG_FUNCTION_ARGS)
 
Datum network_gt (PG_FUNCTION_ARGS)
 
Datum network_ne (PG_FUNCTION_ARGS)
 
Datum network_smaller (PG_FUNCTION_ARGS)
 
Datum network_larger (PG_FUNCTION_ARGS)
 
Datum hashinet (PG_FUNCTION_ARGS)
 
Datum hashinetextended (PG_FUNCTION_ARGS)
 
Datum network_sub (PG_FUNCTION_ARGS)
 
Datum network_subeq (PG_FUNCTION_ARGS)
 
Datum network_sup (PG_FUNCTION_ARGS)
 
Datum network_supeq (PG_FUNCTION_ARGS)
 
Datum network_overlap (PG_FUNCTION_ARGS)
 
Datum network_subset_support (PG_FUNCTION_ARGS)
 
Datum network_host (PG_FUNCTION_ARGS)
 
Datum network_show (PG_FUNCTION_ARGS)
 
Datum inet_abbrev (PG_FUNCTION_ARGS)
 
Datum cidr_abbrev (PG_FUNCTION_ARGS)
 
Datum network_masklen (PG_FUNCTION_ARGS)
 
Datum network_family (PG_FUNCTION_ARGS)
 
Datum network_broadcast (PG_FUNCTION_ARGS)
 
Datum network_network (PG_FUNCTION_ARGS)
 
Datum network_netmask (PG_FUNCTION_ARGS)
 
Datum network_hostmask (PG_FUNCTION_ARGS)
 
Datum inet_same_family (PG_FUNCTION_ARGS)
 
Datum inet_merge (PG_FUNCTION_ARGS)
 
double convert_network_to_scalar (Datum value, Oid typid, bool *failure)
 
int bitncmp (const unsigned char *l, const unsigned char *r, int n)
 
int bitncommon (const unsigned char *l, const unsigned char *r, int n)
 
Datum network_scan_first (Datum in)
 
Datum network_scan_last (Datum in)
 
Datum inet_client_addr (PG_FUNCTION_ARGS)
 
Datum inet_client_port (PG_FUNCTION_ARGS)
 
Datum inet_server_addr (PG_FUNCTION_ARGS)
 
Datum inet_server_port (PG_FUNCTION_ARGS)
 
Datum inetnot (PG_FUNCTION_ARGS)
 
Datum inetand (PG_FUNCTION_ARGS)
 
Datum inetor (PG_FUNCTION_ARGS)
 
Datum inetpl (PG_FUNCTION_ARGS)
 
Datum inetmi_int8 (PG_FUNCTION_ARGS)
 
Datum inetmi (PG_FUNCTION_ARGS)
 
void clean_ipv6_addr (int addr_family, char *addr)
 

Macro Definition Documentation

◆ ABBREV_BITS_INET4_NETMASK_SIZE

#define ABBREV_BITS_INET4_NETMASK_SIZE   6

Definition at line 42 of file network.c.

◆ ABBREV_BITS_INET4_SUBNET

#define ABBREV_BITS_INET4_SUBNET   25

Definition at line 43 of file network.c.

Function Documentation

◆ addressOK()

static bool addressOK ( unsigned char *  a,
int  bits,
int  family 
)
static

Definition at line 1635 of file network.c.

1636 {
1637  int byte;
1638  int nbits;
1639  int maxbits;
1640  int maxbytes;
1641  unsigned char mask;
1642 
1643  if (family == PGSQL_AF_INET)
1644  {
1645  maxbits = 32;
1646  maxbytes = 4;
1647  }
1648  else
1649  {
1650  maxbits = 128;
1651  maxbytes = 16;
1652  }
1653  Assert(bits <= maxbits);
1654 
1655  if (bits == maxbits)
1656  return true;
1657 
1658  byte = bits / 8;
1659 
1660  nbits = bits % 8;
1661  mask = 0xff;
1662  if (bits != 0)
1663  mask >>= nbits;
1664 
1665  while (byte < maxbytes)
1666  {
1667  if ((a[byte] & mask) != 0)
1668  return false;
1669  mask = 0xff;
1670  byte++;
1671  }
1672 
1673  return true;
1674 }
#define Assert(condition)
Definition: c.h:849
int a
Definition: isn.c:69
#define PGSQL_AF_INET
Definition: inet.h:39

References a, Assert, and PGSQL_AF_INET.

Referenced by network_in(), and network_recv().

◆ bitncmp()

int bitncmp ( const unsigned char *  l,
const unsigned char *  r,
int  n 
)

Definition at line 1563 of file network.c.

1564 {
1565  unsigned int lb,
1566  rb;
1567  int x,
1568  b;
1569 
1570  b = n / 8;
1571  x = memcmp(l, r, b);
1572  if (x || (n % 8) == 0)
1573  return x;
1574 
1575  lb = l[b];
1576  rb = r[b];
1577  for (b = n % 8; b > 0; b--)
1578  {
1579  if (IS_HIGHBIT_SET(lb) != IS_HIGHBIT_SET(rb))
1580  {
1581  if (IS_HIGHBIT_SET(lb))
1582  return 1;
1583  return -1;
1584  }
1585  lb <<= 1;
1586  rb <<= 1;
1587  }
1588  return 0;
1589 }
#define IS_HIGHBIT_SET(ch)
Definition: c.h:1146
int b
Definition: isn.c:70
int x
Definition: isn.c:71

References b, IS_HIGHBIT_SET, and x.

Referenced by inet_gist_consistent(), inet_inclusion_cmp(), inet_spg_choose(), inet_spg_consistent_bitmap(), network_cmp_internal(), network_overlap(), network_sub(), network_subeq(), network_sup(), and network_supeq().

◆ bitncommon()

int bitncommon ( const unsigned char *  l,
const unsigned char *  r,
int  n 
)

Definition at line 1597 of file network.c.

1598 {
1599  int byte,
1600  nbits;
1601 
1602  /* number of bits to examine in last byte */
1603  nbits = n % 8;
1604 
1605  /* check whole bytes */
1606  for (byte = 0; byte < n / 8; byte++)
1607  {
1608  if (l[byte] != r[byte])
1609  {
1610  /* at least one bit in the last byte is not common */
1611  nbits = 7;
1612  break;
1613  }
1614  }
1615 
1616  /* check bits in last partial byte */
1617  if (nbits != 0)
1618  {
1619  /* calculate diff of first non-matching bytes */
1620  unsigned int diff = l[byte] ^ r[byte];
1621 
1622  /* compare the bits from the most to the least */
1623  while ((diff >> (8 - nbits)) != 0)
1624  nbits--;
1625  }
1626 
1627  return (8 * byte) + nbits;
1628 }

Referenced by calc_inet_union_params(), calc_inet_union_params_indexed(), inet_gist_penalty(), inet_hist_match_divider(), inet_merge(), inet_spg_choose(), and inet_spg_picksplit().

◆ cidr_abbrev()

Datum cidr_abbrev ( PG_FUNCTION_ARGS  )

Definition at line 1234 of file network.c.

1235 {
1236  inet *ip = PG_GETARG_INET_PP(0);
1237  char *dst;
1238  char tmp[sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:255.255.255.255/128")];
1239 
1240  dst = pg_inet_cidr_ntop(ip_family(ip), ip_addr(ip),
1241  ip_bits(ip), tmp, sizeof(tmp));
1242 
1243  if (dst == NULL)
1244  ereport(ERROR,
1245  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
1246  errmsg("could not format cidr value: %m")));
1247 
1249 }
int errcode(int sqlerrcode)
Definition: elog.c:853
int errmsg(const char *fmt,...)
Definition: elog.c:1070
#define ERROR
Definition: elog.h:39
#define ereport(elevel,...)
Definition: elog.h:149
#define PG_RETURN_TEXT_P(x)
Definition: fmgr.h:372
char * pg_inet_cidr_ntop(int af, const void *src, int bits, char *dst, size_t size)
Definition: inet.h:53
#define ip_addr(inetptr)
Definition: inet.h:77
#define PG_GETARG_INET_PP(n)
Definition: inet.h:134
#define ip_family(inetptr)
Definition: inet.h:71
#define ip_bits(inetptr)
Definition: inet.h:74
text * cstring_to_text(const char *s)
Definition: varlena.c:184

References cstring_to_text(), ereport, errcode(), errmsg(), ERROR, ip_addr, ip_bits, ip_family, PG_GETARG_INET_PP, pg_inet_cidr_ntop(), and PG_RETURN_TEXT_P.

◆ cidr_in()

Datum cidr_in ( PG_FUNCTION_ARGS  )

Definition at line 129 of file network.c.

130 {
131  char *src = PG_GETARG_CSTRING(0);
132 
133  PG_RETURN_INET_P(network_in(src, true, fcinfo->context));
134 }
#define PG_GETARG_CSTRING(n)
Definition: fmgr.h:277
static inet * network_in(char *src, bool is_cidr, Node *escontext)
Definition: network.c:75
#define PG_RETURN_INET_P(x)
Definition: inet.h:135

References network_in(), PG_GETARG_CSTRING, and PG_RETURN_INET_P.

◆ cidr_out()

Datum cidr_out ( PG_FUNCTION_ARGS  )

Definition at line 173 of file network.c.

174 {
175  inet *src = PG_GETARG_INET_PP(0);
176 
177  PG_RETURN_CSTRING(network_out(src, true));
178 }
#define PG_RETURN_CSTRING(x)
Definition: fmgr.h:362
static char * network_out(inet *src, bool is_cidr)
Definition: network.c:141

References network_out(), PG_GETARG_INET_PP, and PG_RETURN_CSTRING.

◆ cidr_recv()

Datum cidr_recv ( PG_FUNCTION_ARGS  )

Definition at line 258 of file network.c.

259 {
261 
263 }
#define PG_GETARG_POINTER(n)
Definition: fmgr.h:276
static inet * network_recv(StringInfo buf, bool is_cidr)
Definition: network.c:192
static char * buf
Definition: pg_test_fsync.c:73
StringInfoData * StringInfo
Definition: stringinfo.h:54

References buf, network_recv(), PG_GETARG_POINTER, and PG_RETURN_INET_P.

◆ cidr_send()

Datum cidr_send ( PG_FUNCTION_ARGS  )

Definition at line 300 of file network.c.

301 {
302  inet *addr = PG_GETARG_INET_PP(0);
303 
304  PG_RETURN_BYTEA_P(network_send(addr, true));
305 }
#define PG_RETURN_BYTEA_P(x)
Definition: fmgr.h:371
static bytea * network_send(inet *addr, bool is_cidr)
Definition: network.c:270

References network_send(), PG_GETARG_INET_PP, and PG_RETURN_BYTEA_P.

◆ cidr_set_masklen()

Datum cidr_set_masklen ( PG_FUNCTION_ARGS  )

Definition at line 348 of file network.c.

349 {
350  inet *src = PG_GETARG_INET_PP(0);
351  int bits = PG_GETARG_INT32(1);
352 
353  if (bits == -1)
354  bits = ip_maxbits(src);
355 
356  if ((bits < 0) || (bits > ip_maxbits(src)))
357  ereport(ERROR,
358  (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
359  errmsg("invalid mask length: %d", bits)));
360 
362 }
#define PG_GETARG_INT32(n)
Definition: fmgr.h:269
inet * cidr_set_masklen_internal(const inet *src, int bits)
Definition: network.c:368
#define ip_maxbits(inetptr)
Definition: inet.h:83

References cidr_set_masklen_internal(), ereport, errcode(), errmsg(), ERROR, ip_maxbits, PG_GETARG_INET_PP, PG_GETARG_INT32, and PG_RETURN_INET_P.

◆ cidr_set_masklen_internal()

inet* cidr_set_masklen_internal ( const inet src,
int  bits 
)

Definition at line 368 of file network.c.

369 {
370  inet *dst = (inet *) palloc0(sizeof(inet));
371 
372  ip_family(dst) = ip_family(src);
373  ip_bits(dst) = bits;
374 
375  if (bits > 0)
376  {
377  Assert(bits <= ip_maxbits(dst));
378 
379  /* Clone appropriate bytes of the address, leaving the rest 0 */
380  memcpy(ip_addr(dst), ip_addr(src), (bits + 7) / 8);
381 
382  /* Clear any unwanted bits in the last partial byte */
383  if (bits % 8)
384  ip_addr(dst)[bits / 8] &= ~(0xFF >> (bits % 8));
385  }
386 
387  /* Set varlena header correctly */
388  SET_INET_VARSIZE(dst);
389 
390  return dst;
391 }
void * palloc0(Size size)
Definition: mcxt.c:1347
#define SET_INET_VARSIZE(dst)
Definition: inet.h:86

References Assert, ip_addr, ip_bits, ip_family, ip_maxbits, palloc0(), and SET_INET_VARSIZE.

Referenced by cidr_set_masklen(), inet_merge(), inet_spg_choose(), inet_spg_picksplit(), and inet_to_cidr().

◆ clean_ipv6_addr()

void clean_ipv6_addr ( int  addr_family,
char *  addr 
)

Definition at line 2089 of file network.c.

2090 {
2091  if (addr_family == AF_INET6)
2092  {
2093  char *pct = strchr(addr, '%');
2094 
2095  if (pct)
2096  *pct = '\0';
2097  }
2098 }

Referenced by fill_hba_line(), inet_client_addr(), inet_server_addr(), pg_stat_get_activity(), and pg_stat_get_backend_client_addr().

◆ convert_network_to_scalar()

double convert_network_to_scalar ( Datum  value,
Oid  typid,
bool failure 
)

Definition at line 1496 of file network.c.

1497 {
1498  switch (typid)
1499  {
1500  case INETOID:
1501  case CIDROID:
1502  {
1503  inet *ip = DatumGetInetPP(value);
1504  int len;
1505  double res;
1506  int i;
1507 
1508  /*
1509  * Note that we don't use the full address for IPv6.
1510  */
1511  if (ip_family(ip) == PGSQL_AF_INET)
1512  len = 4;
1513  else
1514  len = 5;
1515 
1516  res = ip_family(ip);
1517  for (i = 0; i < len; i++)
1518  {
1519  res *= 256;
1520  res += ip_addr(ip)[i];
1521  }
1522  return res;
1523  }
1524  case MACADDROID:
1525  {
1526  macaddr *mac = DatumGetMacaddrP(value);
1527  double res;
1528 
1529  res = (mac->a << 16) | (mac->b << 8) | (mac->c);
1530  res *= 256 * 256 * 256;
1531  res += (mac->d << 16) | (mac->e << 8) | (mac->f);
1532  return res;
1533  }
1534  case MACADDR8OID:
1535  {
1537  double res;
1538 
1539  res = (mac->a << 24) | (mac->b << 16) | (mac->c << 8) | (mac->d);
1540  res *= ((double) 256) * 256 * 256 * 256;
1541  res += (mac->e << 24) | (mac->f << 16) | (mac->g << 8) | (mac->h);
1542  return res;
1543  }
1544  }
1545 
1546  *failure = true;
1547  return 0;
1548 }
static struct @157 value
int i
Definition: isn.c:73
const void size_t len
Definition: inet.h:108
unsigned char c
Definition: inet.h:111
unsigned char b
Definition: inet.h:110
unsigned char d
Definition: inet.h:112
unsigned char e
Definition: inet.h:113
unsigned char g
Definition: inet.h:115
unsigned char h
Definition: inet.h:116
unsigned char a
Definition: inet.h:109
unsigned char f
Definition: inet.h:114
Definition: inet.h:95
unsigned char e
Definition: inet.h:100
unsigned char b
Definition: inet.h:97
unsigned char f
Definition: inet.h:101
unsigned char c
Definition: inet.h:98
unsigned char a
Definition: inet.h:96
unsigned char d
Definition: inet.h:99
static macaddr * DatumGetMacaddrP(Datum X)
Definition: inet.h:147
static inet * DatumGetInetPP(Datum X)
Definition: inet.h:123
static macaddr8 * DatumGetMacaddr8P(Datum X)
Definition: inet.h:163

References macaddr::a, macaddr8::a, macaddr::b, macaddr8::b, macaddr::c, macaddr8::c, macaddr::d, macaddr8::d, DatumGetInetPP(), DatumGetMacaddr8P(), DatumGetMacaddrP(), macaddr::e, macaddr8::e, macaddr::f, macaddr8::f, macaddr8::g, macaddr8::h, i, ip_addr, ip_family, len, PGSQL_AF_INET, res, and value.

Referenced by convert_to_scalar(), gbt_inet_compress(), and gbt_inet_consistent().

◆ hashinet()

Datum hashinet ( PG_FUNCTION_ARGS  )

Definition at line 874 of file network.c.

875 {
876  inet *addr = PG_GETARG_INET_PP(0);
877  int addrsize = ip_addrsize(addr);
878 
879  /* XXX this assumes there are no pad bytes in the data structure */
880  return hash_any((unsigned char *) VARDATA_ANY(addr), addrsize + 2);
881 }
static Datum hash_any(const unsigned char *k, int keylen)
Definition: hashfn.h:31
#define ip_addrsize(inetptr)
Definition: inet.h:80
#define VARDATA_ANY(PTR)
Definition: varatt.h:324

References hash_any(), ip_addrsize, PG_GETARG_INET_PP, and VARDATA_ANY.

◆ hashinetextended()

Datum hashinetextended ( PG_FUNCTION_ARGS  )

Definition at line 884 of file network.c.

885 {
886  inet *addr = PG_GETARG_INET_PP(0);
887  int addrsize = ip_addrsize(addr);
888 
889  return hash_any_extended((unsigned char *) VARDATA_ANY(addr), addrsize + 2,
890  PG_GETARG_INT64(1));
891 }
#define PG_GETARG_INT64(n)
Definition: fmgr.h:283
static Datum hash_any_extended(const unsigned char *k, int keylen, uint64 seed)
Definition: hashfn.h:37

References hash_any_extended(), ip_addrsize, PG_GETARG_INET_PP, PG_GETARG_INT64, and VARDATA_ANY.

◆ inet_abbrev()

Datum inet_abbrev ( PG_FUNCTION_ARGS  )

Definition at line 1216 of file network.c.

1217 {
1218  inet *ip = PG_GETARG_INET_PP(0);
1219  char *dst;
1220  char tmp[sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:255.255.255.255/128")];
1221 
1222  dst = pg_inet_net_ntop(ip_family(ip), ip_addr(ip),
1223  ip_bits(ip), tmp, sizeof(tmp));
1224 
1225  if (dst == NULL)
1226  ereport(ERROR,
1227  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
1228  errmsg("could not format inet value: %m")));
1229 
1231 }
char * pg_inet_net_ntop(int af, const void *src, int bits, char *dst, size_t size)
Definition: inet_net_ntop.c:77

References cstring_to_text(), ereport, errcode(), errmsg(), ERROR, ip_addr, ip_bits, ip_family, PG_GETARG_INET_PP, pg_inet_net_ntop(), and PG_RETURN_TEXT_P.

◆ inet_client_addr()

Datum inet_client_addr ( PG_FUNCTION_ARGS  )

Definition at line 1710 of file network.c.

1711 {
1712  Port *port = MyProcPort;
1713  char remote_host[NI_MAXHOST];
1714  int ret;
1715 
1716  if (port == NULL)
1717  PG_RETURN_NULL();
1718 
1719  switch (port->raddr.addr.ss_family)
1720  {
1721  case AF_INET:
1722  case AF_INET6:
1723  break;
1724  default:
1725  PG_RETURN_NULL();
1726  }
1727 
1728  remote_host[0] = '\0';
1729 
1730  ret = pg_getnameinfo_all(&port->raddr.addr, port->raddr.salen,
1731  remote_host, sizeof(remote_host),
1732  NULL, 0,
1733  NI_NUMERICHOST | NI_NUMERICSERV);
1734  if (ret != 0)
1735  PG_RETURN_NULL();
1736 
1737  clean_ipv6_addr(port->raddr.addr.ss_family, remote_host);
1738 
1739  PG_RETURN_INET_P(network_in(remote_host, false, NULL));
1740 }
#define PG_RETURN_NULL()
Definition: fmgr.h:345
struct Port * MyProcPort
Definition: globals.c:50
int pg_getnameinfo_all(const struct sockaddr_storage *addr, int salen, char *node, int nodelen, char *service, int servicelen, int flags)
Definition: ip.c:114
void clean_ipv6_addr(int addr_family, char *addr)
Definition: network.c:2089
static int port
Definition: pg_regress.c:116
Definition: libpq-be.h:133

References clean_ipv6_addr(), MyProcPort, network_in(), pg_getnameinfo_all(), PG_RETURN_INET_P, PG_RETURN_NULL, and port.

◆ inet_client_port()

Datum inet_client_port ( PG_FUNCTION_ARGS  )

Definition at line 1747 of file network.c.

1748 {
1749  Port *port = MyProcPort;
1750  char remote_port[NI_MAXSERV];
1751  int ret;
1752 
1753  if (port == NULL)
1754  PG_RETURN_NULL();
1755 
1756  switch (port->raddr.addr.ss_family)
1757  {
1758  case AF_INET:
1759  case AF_INET6:
1760  break;
1761  default:
1762  PG_RETURN_NULL();
1763  }
1764 
1765  remote_port[0] = '\0';
1766 
1767  ret = pg_getnameinfo_all(&port->raddr.addr, port->raddr.salen,
1768  NULL, 0,
1769  remote_port, sizeof(remote_port),
1770  NI_NUMERICHOST | NI_NUMERICSERV);
1771  if (ret != 0)
1772  PG_RETURN_NULL();
1773 
1775 }
#define DirectFunctionCall1(func, arg1)
Definition: fmgr.h:641
#define PG_RETURN_DATUM(x)
Definition: fmgr.h:353
Datum int4in(PG_FUNCTION_ARGS)
Definition: int.c:287
static Datum CStringGetDatum(const char *X)
Definition: postgres.h:350

References CStringGetDatum(), DirectFunctionCall1, int4in(), MyProcPort, pg_getnameinfo_all(), PG_RETURN_DATUM, PG_RETURN_NULL, and port.

◆ inet_in()

Datum inet_in ( PG_FUNCTION_ARGS  )

Definition at line 121 of file network.c.

122 {
123  char *src = PG_GETARG_CSTRING(0);
124 
125  PG_RETURN_INET_P(network_in(src, false, fcinfo->context));
126 }

References network_in(), PG_GETARG_CSTRING, and PG_RETURN_INET_P.

Referenced by leftmostvalue_inet(), pg_stat_get_activity(), and pg_stat_get_backend_client_addr().

◆ inet_merge()

Datum inet_merge ( PG_FUNCTION_ARGS  )

Definition at line 1470 of file network.c.

1471 {
1472  inet *a1 = PG_GETARG_INET_PP(0),
1473  *a2 = PG_GETARG_INET_PP(1);
1474  int commonbits;
1475 
1476  if (ip_family(a1) != ip_family(a2))
1477  ereport(ERROR,
1478  (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1479  errmsg("cannot merge addresses from different families")));
1480 
1481  commonbits = bitncommon(ip_addr(a1), ip_addr(a2),
1482  Min(ip_bits(a1), ip_bits(a2)));
1483 
1485 }
#define Min(x, y)
Definition: c.h:995
static const FormData_pg_attribute a1
Definition: heap.c:142
static const FormData_pg_attribute a2
Definition: heap.c:156
int bitncommon(const unsigned char *l, const unsigned char *r, int n)
Definition: network.c:1597

References a1, a2, bitncommon(), cidr_set_masklen_internal(), ereport, errcode(), errmsg(), ERROR, ip_addr, ip_bits, ip_family, Min, PG_GETARG_INET_PP, and PG_RETURN_INET_P.

◆ inet_out()

Datum inet_out ( PG_FUNCTION_ARGS  )

Definition at line 165 of file network.c.

166 {
167  inet *src = PG_GETARG_INET_PP(0);
168 
169  PG_RETURN_CSTRING(network_out(src, false));
170 }

References network_out(), PG_GETARG_INET_PP, and PG_RETURN_CSTRING.

◆ inet_recv()

Datum inet_recv ( PG_FUNCTION_ARGS  )

Definition at line 250 of file network.c.

251 {
253 
255 }

References buf, network_recv(), PG_GETARG_POINTER, and PG_RETURN_INET_P.

◆ inet_same_family()

Datum inet_same_family ( PG_FUNCTION_ARGS  )

Definition at line 1458 of file network.c.

1459 {
1460  inet *a1 = PG_GETARG_INET_PP(0);
1461  inet *a2 = PG_GETARG_INET_PP(1);
1462 
1464 }
#define PG_RETURN_BOOL(x)
Definition: fmgr.h:359

References a1, a2, ip_family, PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ inet_send()

Datum inet_send ( PG_FUNCTION_ARGS  )

Definition at line 292 of file network.c.

293 {
294  inet *addr = PG_GETARG_INET_PP(0);
295 
296  PG_RETURN_BYTEA_P(network_send(addr, false));
297 }

References network_send(), PG_GETARG_INET_PP, and PG_RETURN_BYTEA_P.

◆ inet_server_addr()

Datum inet_server_addr ( PG_FUNCTION_ARGS  )

Definition at line 1782 of file network.c.

1783 {
1784  Port *port = MyProcPort;
1785  char local_host[NI_MAXHOST];
1786  int ret;
1787 
1788  if (port == NULL)
1789  PG_RETURN_NULL();
1790 
1791  switch (port->laddr.addr.ss_family)
1792  {
1793  case AF_INET:
1794  case AF_INET6:
1795  break;
1796  default:
1797  PG_RETURN_NULL();
1798  }
1799 
1800  local_host[0] = '\0';
1801 
1802  ret = pg_getnameinfo_all(&port->laddr.addr, port->laddr.salen,
1803  local_host, sizeof(local_host),
1804  NULL, 0,
1805  NI_NUMERICHOST | NI_NUMERICSERV);
1806  if (ret != 0)
1807  PG_RETURN_NULL();
1808 
1809  clean_ipv6_addr(port->laddr.addr.ss_family, local_host);
1810 
1811  PG_RETURN_INET_P(network_in(local_host, false, NULL));
1812 }

References clean_ipv6_addr(), MyProcPort, network_in(), pg_getnameinfo_all(), PG_RETURN_INET_P, PG_RETURN_NULL, and port.

◆ inet_server_port()

Datum inet_server_port ( PG_FUNCTION_ARGS  )

Definition at line 1819 of file network.c.

1820 {
1821  Port *port = MyProcPort;
1822  char local_port[NI_MAXSERV];
1823  int ret;
1824 
1825  if (port == NULL)
1826  PG_RETURN_NULL();
1827 
1828  switch (port->laddr.addr.ss_family)
1829  {
1830  case AF_INET:
1831  case AF_INET6:
1832  break;
1833  default:
1834  PG_RETURN_NULL();
1835  }
1836 
1837  local_port[0] = '\0';
1838 
1839  ret = pg_getnameinfo_all(&port->laddr.addr, port->laddr.salen,
1840  NULL, 0,
1841  local_port, sizeof(local_port),
1842  NI_NUMERICHOST | NI_NUMERICSERV);
1843  if (ret != 0)
1844  PG_RETURN_NULL();
1845 
1847 }

References CStringGetDatum(), DirectFunctionCall1, int4in(), MyProcPort, pg_getnameinfo_all(), PG_RETURN_DATUM, PG_RETURN_NULL, and port.

◆ inet_set_masklen()

Datum inet_set_masklen ( PG_FUNCTION_ARGS  )

Definition at line 324 of file network.c.

325 {
326  inet *src = PG_GETARG_INET_PP(0);
327  int bits = PG_GETARG_INT32(1);
328  inet *dst;
329 
330  if (bits == -1)
331  bits = ip_maxbits(src);
332 
333  if ((bits < 0) || (bits > ip_maxbits(src)))
334  ereport(ERROR,
335  (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
336  errmsg("invalid mask length: %d", bits)));
337 
338  /* clone the original data */
339  dst = (inet *) palloc(VARSIZE_ANY(src));
340  memcpy(dst, src, VARSIZE_ANY(src));
341 
342  ip_bits(dst) = bits;
343 
344  PG_RETURN_INET_P(dst);
345 }
void * palloc(Size size)
Definition: mcxt.c:1317
#define VARSIZE_ANY(PTR)
Definition: varatt.h:311

References ereport, errcode(), errmsg(), ERROR, ip_bits, ip_maxbits, palloc(), PG_GETARG_INET_PP, PG_GETARG_INT32, PG_RETURN_INET_P, and VARSIZE_ANY.

Referenced by network_scan_last().

◆ inet_to_cidr()

Datum inet_to_cidr ( PG_FUNCTION_ARGS  )

Definition at line 309 of file network.c.

310 {
311  inet *src = PG_GETARG_INET_PP(0);
312  int bits;
313 
314  bits = ip_bits(src);
315 
316  /* safety check */
317  if ((bits < 0) || (bits > ip_maxbits(src)))
318  elog(ERROR, "invalid inet bit length: %d", bits);
319 
321 }
#define elog(elevel,...)
Definition: elog.h:225

References cidr_set_masklen_internal(), elog, ERROR, ip_bits, ip_maxbits, PG_GETARG_INET_PP, and PG_RETURN_INET_P.

◆ inetand()

Datum inetand ( PG_FUNCTION_ARGS  )

Definition at line 1876 of file network.c.

1877 {
1878  inet *ip = PG_GETARG_INET_PP(0);
1879  inet *ip2 = PG_GETARG_INET_PP(1);
1880  inet *dst;
1881 
1882  dst = (inet *) palloc0(sizeof(inet));
1883 
1884  if (ip_family(ip) != ip_family(ip2))
1885  ereport(ERROR,
1886  (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1887  errmsg("cannot AND inet values of different sizes")));
1888  else
1889  {
1890  int nb = ip_addrsize(ip);
1891  unsigned char *pip = ip_addr(ip);
1892  unsigned char *pip2 = ip_addr(ip2);
1893  unsigned char *pdst = ip_addr(dst);
1894 
1895  while (--nb >= 0)
1896  pdst[nb] = pip[nb] & pip2[nb];
1897  }
1898  ip_bits(dst) = Max(ip_bits(ip), ip_bits(ip2));
1899 
1900  ip_family(dst) = ip_family(ip);
1901  SET_INET_VARSIZE(dst);
1902 
1903  PG_RETURN_INET_P(dst);
1904 }
#define Max(x, y)
Definition: c.h:989

References ereport, errcode(), errmsg(), ERROR, ip_addr, ip_addrsize, ip_bits, ip_family, Max, palloc0(), PG_GETARG_INET_PP, PG_RETURN_INET_P, and SET_INET_VARSIZE.

◆ inetmi()

Datum inetmi ( PG_FUNCTION_ARGS  )

Definition at line 2012 of file network.c.

2013 {
2014  inet *ip = PG_GETARG_INET_PP(0);
2015  inet *ip2 = PG_GETARG_INET_PP(1);
2016  int64 res = 0;
2017 
2018  if (ip_family(ip) != ip_family(ip2))
2019  ereport(ERROR,
2020  (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
2021  errmsg("cannot subtract inet values of different sizes")));
2022  else
2023  {
2024  /*
2025  * We form the difference using the traditional complement, increment,
2026  * and add rule, with the increment part being handled by starting the
2027  * carry off at 1. If you don't think integer arithmetic is done in
2028  * two's complement, too bad.
2029  */
2030  int nb = ip_addrsize(ip);
2031  int byte = 0;
2032  unsigned char *pip = ip_addr(ip);
2033  unsigned char *pip2 = ip_addr(ip2);
2034  int carry = 1;
2035 
2036  while (--nb >= 0)
2037  {
2038  int lobyte;
2039 
2040  carry = pip[nb] + (~pip2[nb] & 0xFF) + carry;
2041  lobyte = carry & 0xFF;
2042  if (byte < sizeof(int64))
2043  {
2044  res |= ((int64) lobyte) << (byte * 8);
2045  }
2046  else
2047  {
2048  /*
2049  * Input wider than int64: check for overflow. All bytes to
2050  * the left of what will fit should be 0 or 0xFF, depending on
2051  * sign of the now-complete result.
2052  */
2053  if ((res < 0) ? (lobyte != 0xFF) : (lobyte != 0))
2054  ereport(ERROR,
2055  (errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
2056  errmsg("result is out of range")));
2057  }
2058  carry >>= 8;
2059  byte++;
2060  }
2061 
2062  /*
2063  * If input is narrower than int64, overflow is not possible, but we
2064  * have to do proper sign extension.
2065  */
2066  if (carry == 0 && byte < sizeof(int64))
2067  res |= ((uint64) (int64) -1) << (byte * 8);
2068  }
2069 
2071 }
#define PG_RETURN_INT64(x)
Definition: fmgr.h:368

References ereport, errcode(), errmsg(), ERROR, ip_addr, ip_addrsize, ip_family, PG_GETARG_INET_PP, PG_RETURN_INT64, and res.

◆ inetmi_int8()

Datum inetmi_int8 ( PG_FUNCTION_ARGS  )

Definition at line 2002 of file network.c.

2003 {
2004  inet *ip = PG_GETARG_INET_PP(0);
2005  int64 addend = PG_GETARG_INT64(1);
2006 
2007  PG_RETURN_INET_P(internal_inetpl(ip, -addend));
2008 }
static inet * internal_inetpl(inet *ip, int64 addend)
Definition: network.c:1940

References internal_inetpl(), PG_GETARG_INET_PP, PG_GETARG_INT64, and PG_RETURN_INET_P.

◆ inetnot()

Datum inetnot ( PG_FUNCTION_ARGS  )

Definition at line 1851 of file network.c.

1852 {
1853  inet *ip = PG_GETARG_INET_PP(0);
1854  inet *dst;
1855 
1856  dst = (inet *) palloc0(sizeof(inet));
1857 
1858  {
1859  int nb = ip_addrsize(ip);
1860  unsigned char *pip = ip_addr(ip);
1861  unsigned char *pdst = ip_addr(dst);
1862 
1863  while (--nb >= 0)
1864  pdst[nb] = ~pip[nb];
1865  }
1866  ip_bits(dst) = ip_bits(ip);
1867 
1868  ip_family(dst) = ip_family(ip);
1869  SET_INET_VARSIZE(dst);
1870 
1871  PG_RETURN_INET_P(dst);
1872 }

References ip_addr, ip_addrsize, ip_bits, ip_family, palloc0(), PG_GETARG_INET_PP, PG_RETURN_INET_P, and SET_INET_VARSIZE.

◆ inetor()

Datum inetor ( PG_FUNCTION_ARGS  )

Definition at line 1908 of file network.c.

1909 {
1910  inet *ip = PG_GETARG_INET_PP(0);
1911  inet *ip2 = PG_GETARG_INET_PP(1);
1912  inet *dst;
1913 
1914  dst = (inet *) palloc0(sizeof(inet));
1915 
1916  if (ip_family(ip) != ip_family(ip2))
1917  ereport(ERROR,
1918  (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
1919  errmsg("cannot OR inet values of different sizes")));
1920  else
1921  {
1922  int nb = ip_addrsize(ip);
1923  unsigned char *pip = ip_addr(ip);
1924  unsigned char *pip2 = ip_addr(ip2);
1925  unsigned char *pdst = ip_addr(dst);
1926 
1927  while (--nb >= 0)
1928  pdst[nb] = pip[nb] | pip2[nb];
1929  }
1930  ip_bits(dst) = Max(ip_bits(ip), ip_bits(ip2));
1931 
1932  ip_family(dst) = ip_family(ip);
1933  SET_INET_VARSIZE(dst);
1934 
1935  PG_RETURN_INET_P(dst);
1936 }

References ereport, errcode(), errmsg(), ERROR, ip_addr, ip_addrsize, ip_bits, ip_family, Max, palloc0(), PG_GETARG_INET_PP, PG_RETURN_INET_P, and SET_INET_VARSIZE.

◆ inetpl()

Datum inetpl ( PG_FUNCTION_ARGS  )

Definition at line 1992 of file network.c.

1993 {
1994  inet *ip = PG_GETARG_INET_PP(0);
1995  int64 addend = PG_GETARG_INT64(1);
1996 
1997  PG_RETURN_INET_P(internal_inetpl(ip, addend));
1998 }

References internal_inetpl(), PG_GETARG_INET_PP, PG_GETARG_INT64, and PG_RETURN_INET_P.

◆ internal_inetpl()

static inet * internal_inetpl ( inet ip,
int64  addend 
)
static

Definition at line 1940 of file network.c.

1941 {
1942  inet *dst;
1943 
1944  dst = (inet *) palloc0(sizeof(inet));
1945 
1946  {
1947  int nb = ip_addrsize(ip);
1948  unsigned char *pip = ip_addr(ip);
1949  unsigned char *pdst = ip_addr(dst);
1950  int carry = 0;
1951 
1952  while (--nb >= 0)
1953  {
1954  carry = pip[nb] + (int) (addend & 0xFF) + carry;
1955  pdst[nb] = (unsigned char) (carry & 0xFF);
1956  carry >>= 8;
1957 
1958  /*
1959  * We have to be careful about right-shifting addend because
1960  * right-shift isn't portable for negative values, while simply
1961  * dividing by 256 doesn't work (the standard rounding is in the
1962  * wrong direction, besides which there may be machines out there
1963  * that round the wrong way). So, explicitly clear the low-order
1964  * byte to remove any doubt about the correct result of the
1965  * division, and then divide rather than shift.
1966  */
1967  addend &= ~((int64) 0xFF);
1968  addend /= 0x100;
1969  }
1970 
1971  /*
1972  * At this point we should have addend and carry both zero if original
1973  * addend was >= 0, or addend -1 and carry 1 if original addend was <
1974  * 0. Anything else means overflow.
1975  */
1976  if (!((addend == 0 && carry == 0) ||
1977  (addend == -1 && carry == 1)))
1978  ereport(ERROR,
1979  (errcode(ERRCODE_NUMERIC_VALUE_OUT_OF_RANGE),
1980  errmsg("result is out of range")));
1981  }
1982 
1983  ip_bits(dst) = ip_bits(ip);
1984  ip_family(dst) = ip_family(ip);
1985  SET_INET_VARSIZE(dst);
1986 
1987  return dst;
1988 }

References ereport, errcode(), errmsg(), ERROR, ip_addr, ip_addrsize, ip_bits, ip_family, palloc0(), and SET_INET_VARSIZE.

Referenced by inetmi_int8(), and inetpl().

◆ match_network_function()

static List * match_network_function ( Node leftop,
Node rightop,
int  indexarg,
Oid  funcid,
Oid  opfamily 
)
static

Definition at line 1022 of file network.c.

1027 {
1028  switch (funcid)
1029  {
1030  case F_NETWORK_SUB:
1031  /* indexkey must be on the left */
1032  if (indexarg != 0)
1033  return NIL;
1034  return match_network_subset(leftop, rightop, false, opfamily);
1035 
1036  case F_NETWORK_SUBEQ:
1037  /* indexkey must be on the left */
1038  if (indexarg != 0)
1039  return NIL;
1040  return match_network_subset(leftop, rightop, true, opfamily);
1041 
1042  case F_NETWORK_SUP:
1043  /* indexkey must be on the right */
1044  if (indexarg != 1)
1045  return NIL;
1046  return match_network_subset(rightop, leftop, false, opfamily);
1047 
1048  case F_NETWORK_SUPEQ:
1049  /* indexkey must be on the right */
1050  if (indexarg != 1)
1051  return NIL;
1052  return match_network_subset(rightop, leftop, true, opfamily);
1053 
1054  default:
1055 
1056  /*
1057  * We'd only get here if somebody attached this support function
1058  * to an unexpected function. Maybe we should complain, but for
1059  * now, do nothing.
1060  */
1061  return NIL;
1062  }
1063 }
static List * match_network_subset(Node *leftop, Node *rightop, bool is_eq, Oid opfamily)
Definition: network.c:1070
#define NIL
Definition: pg_list.h:68

References match_network_subset(), and NIL.

Referenced by network_subset_support().

◆ match_network_subset()

static List * match_network_subset ( Node leftop,
Node rightop,
bool  is_eq,
Oid  opfamily 
)
static

Definition at line 1070 of file network.c.

1074 {
1075  List *result;
1076  Datum rightopval;
1077  Oid datatype = INETOID;
1078  Oid opr1oid;
1079  Oid opr2oid;
1080  Datum opr1right;
1081  Datum opr2right;
1082  Expr *expr;
1083 
1084  /*
1085  * Can't do anything with a non-constant or NULL comparison value.
1086  *
1087  * Note that since we restrict ourselves to cases with a hard constant on
1088  * the RHS, it's a-fortiori a pseudoconstant, and we don't need to worry
1089  * about verifying that.
1090  */
1091  if (!IsA(rightop, Const) ||
1092  ((Const *) rightop)->constisnull)
1093  return NIL;
1094  rightopval = ((Const *) rightop)->constvalue;
1095 
1096  /*
1097  * Must check that index's opfamily supports the operators we will want to
1098  * apply.
1099  *
1100  * We insist on the opfamily being the specific one we expect, else we'd
1101  * do the wrong thing if someone were to make a reverse-sort opfamily with
1102  * the same operators.
1103  */
1104  if (opfamily != NETWORK_BTREE_FAM_OID)
1105  return NIL;
1106 
1107  /*
1108  * create clause "key >= network_scan_first( rightopval )", or ">" if the
1109  * operator disallows equality.
1110  *
1111  * Note: seeing that this function supports only fixed values for opfamily
1112  * and datatype, we could just hard-wire the operator OIDs instead of
1113  * looking them up. But for now it seems better to be general.
1114  */
1115  if (is_eq)
1116  {
1117  opr1oid = get_opfamily_member(opfamily, datatype, datatype,
1119  if (opr1oid == InvalidOid)
1120  elog(ERROR, "no >= operator for opfamily %u", opfamily);
1121  }
1122  else
1123  {
1124  opr1oid = get_opfamily_member(opfamily, datatype, datatype,
1126  if (opr1oid == InvalidOid)
1127  elog(ERROR, "no > operator for opfamily %u", opfamily);
1128  }
1129 
1130  opr1right = network_scan_first(rightopval);
1131 
1132  expr = make_opclause(opr1oid, BOOLOID, false,
1133  (Expr *) leftop,
1134  (Expr *) makeConst(datatype, -1,
1135  InvalidOid, /* not collatable */
1136  -1, opr1right,
1137  false, false),
1139  result = list_make1(expr);
1140 
1141  /* create clause "key <= network_scan_last( rightopval )" */
1142 
1143  opr2oid = get_opfamily_member(opfamily, datatype, datatype,
1145  if (opr2oid == InvalidOid)
1146  elog(ERROR, "no <= operator for opfamily %u", opfamily);
1147 
1148  opr2right = network_scan_last(rightopval);
1149 
1150  expr = make_opclause(opr2oid, BOOLOID, false,
1151  (Expr *) leftop,
1152  (Expr *) makeConst(datatype, -1,
1153  InvalidOid, /* not collatable */
1154  -1, opr2right,
1155  false, false),
1157  result = lappend(result, expr);
1158 
1159  return result;
1160 }
List * lappend(List *list, void *datum)
Definition: list.c:339
Oid get_opfamily_member(Oid opfamily, Oid lefttype, Oid righttype, int16 strategy)
Definition: lsyscache.c:166
Expr * make_opclause(Oid opno, Oid opresulttype, bool opretset, Expr *leftop, Expr *rightop, Oid opcollid, Oid inputcollid)
Definition: makefuncs.c:628
Const * makeConst(Oid consttype, int32 consttypmod, Oid constcollid, int constlen, Datum constvalue, bool constisnull, bool constbyval)
Definition: makefuncs.c:301
Datum network_scan_last(Datum in)
Definition: network.c:1698
Datum network_scan_first(Datum in)
Definition: network.c:1684
#define IsA(nodeptr, _type_)
Definition: nodes.h:158
#define list_make1(x1)
Definition: pg_list.h:212
uintptr_t Datum
Definition: postgres.h:64
#define InvalidOid
Definition: postgres_ext.h:36
unsigned int Oid
Definition: postgres_ext.h:31
#define BTGreaterStrategyNumber
Definition: stratnum.h:33
#define BTLessEqualStrategyNumber
Definition: stratnum.h:30
#define BTGreaterEqualStrategyNumber
Definition: stratnum.h:32
Definition: pg_list.h:54

References BTGreaterEqualStrategyNumber, BTGreaterStrategyNumber, BTLessEqualStrategyNumber, elog, ERROR, get_opfamily_member(), InvalidOid, IsA, lappend(), list_make1, make_opclause(), makeConst(), network_scan_first(), network_scan_last(), and NIL.

Referenced by match_network_function().

◆ network_abbrev_abort()

static bool network_abbrev_abort ( int  memtupcount,
SortSupport  ssup 
)
static

Definition at line 488 of file network.c.

489 {
491  double abbr_card;
492 
493  if (memtupcount < 10000 || uss->input_count < 10000 || !uss->estimating)
494  return false;
495 
496  abbr_card = estimateHyperLogLog(&uss->abbr_card);
497 
498  /*
499  * If we have >100k distinct values, then even if we were sorting many
500  * billion rows we'd likely still break even, and the penalty of undoing
501  * that many rows of abbrevs would probably not be worth it. At this point
502  * we stop counting because we know that we're now fully committed.
503  */
504  if (abbr_card > 100000.0)
505  {
506  if (trace_sort)
507  elog(LOG,
508  "network_abbrev: estimation ends at cardinality %f"
509  " after " INT64_FORMAT " values (%d rows)",
510  abbr_card, uss->input_count, memtupcount);
511  uss->estimating = false;
512  return false;
513  }
514 
515  /*
516  * Target minimum cardinality is 1 per ~2k of non-null inputs. 0.5 row
517  * fudge factor allows us to abort earlier on genuinely pathological data
518  * where we've had exactly one abbreviated value in the first 2k
519  * (non-null) rows.
520  */
521  if (abbr_card < uss->input_count / 2000.0 + 0.5)
522  {
523  if (trace_sort)
524  elog(LOG,
525  "network_abbrev: aborting abbreviation at cardinality %f"
526  " below threshold %f after " INT64_FORMAT " values (%d rows)",
527  abbr_card, uss->input_count / 2000.0 + 0.5, uss->input_count,
528  memtupcount);
529  return true;
530  }
531 
532  if (trace_sort)
533  elog(LOG,
534  "network_abbrev: cardinality %f after " INT64_FORMAT
535  " values (%d rows)", abbr_card, uss->input_count, memtupcount);
536 
537  return false;
538 }
#define INT64_FORMAT
Definition: c.h:539
#define LOG
Definition: elog.h:31
double estimateHyperLogLog(hyperLogLogState *cState)
Definition: hyperloglog.c:186
void * ssup_extra
Definition: sortsupport.h:87
hyperLogLogState abbr_card
Definition: network.c:51
bool trace_sort
Definition: tuplesort.c:124

References network_sortsupport_state::abbr_card, elog, estimateHyperLogLog(), network_sortsupport_state::estimating, network_sortsupport_state::input_count, INT64_FORMAT, LOG, SortSupportData::ssup_extra, and trace_sort.

Referenced by network_sortsupport().

◆ network_abbrev_convert()

static Datum network_abbrev_convert ( Datum  original,
SortSupport  ssup 
)
static

Definition at line 619 of file network.c.

620 {
622  inet *authoritative = DatumGetInetPP(original);
623  Datum res,
624  ipaddr_datum,
625  subnet_bitmask,
626  network;
627  int subnet_size;
628 
629  Assert(ip_family(authoritative) == PGSQL_AF_INET ||
630  ip_family(authoritative) == PGSQL_AF_INET6);
631 
632  /*
633  * Get an unsigned integer representation of the IP address by taking its
634  * first 4 or 8 bytes. Always take all 4 bytes of an IPv4 address. Take
635  * the first 8 bytes of an IPv6 address with an 8 byte datum and 4 bytes
636  * otherwise.
637  *
638  * We're consuming an array of unsigned char, so byteswap on little endian
639  * systems (an inet's ipaddr field stores the most significant byte
640  * first).
641  */
642  if (ip_family(authoritative) == PGSQL_AF_INET)
643  {
644  uint32 ipaddr_datum32;
645 
646  memcpy(&ipaddr_datum32, ip_addr(authoritative), sizeof(uint32));
647 
648  /* Must byteswap on little-endian machines */
649 #ifndef WORDS_BIGENDIAN
650  ipaddr_datum = pg_bswap32(ipaddr_datum32);
651 #else
652  ipaddr_datum = ipaddr_datum32;
653 #endif
654 
655  /* Initialize result without setting ipfamily bit */
656  res = (Datum) 0;
657  }
658  else
659  {
660  memcpy(&ipaddr_datum, ip_addr(authoritative), sizeof(Datum));
661 
662  /* Must byteswap on little-endian machines */
663  ipaddr_datum = DatumBigEndianToNative(ipaddr_datum);
664 
665  /* Initialize result with ipfamily (most significant) bit set */
666  res = ((Datum) 1) << (SIZEOF_DATUM * BITS_PER_BYTE - 1);
667  }
668 
669  /*
670  * ipaddr_datum must be "split": high order bits go in "network" component
671  * of abbreviated key (often with zeroed bits at the end due to masking),
672  * while low order bits go in "subnet" component when there is space for
673  * one. This is often accomplished by generating a temp datum subnet
674  * bitmask, which we may reuse later when generating the subnet bits
675  * themselves. (Note that subnet bits are only used with IPv4 datums on
676  * platforms where datum is 8 bytes.)
677  *
678  * The number of bits in subnet is used to generate a datum subnet
679  * bitmask. For example, with a /24 IPv4 datum there are 8 subnet bits
680  * (since 32 - 24 is 8), so the final subnet bitmask is B'1111 1111'. We
681  * need explicit handling for cases where the ipaddr bits cannot all fit
682  * in a datum, though (otherwise we'd incorrectly mask the network
683  * component with IPv6 values).
684  */
685  subnet_size = ip_maxbits(authoritative) - ip_bits(authoritative);
686  Assert(subnet_size >= 0);
687  /* subnet size must work with prefix ipaddr cases */
688  subnet_size %= SIZEOF_DATUM * BITS_PER_BYTE;
689  if (ip_bits(authoritative) == 0)
690  {
691  /* Fit as many ipaddr bits as possible into subnet */
692  subnet_bitmask = ((Datum) 0) - 1;
693  network = 0;
694  }
695  else if (ip_bits(authoritative) < SIZEOF_DATUM * BITS_PER_BYTE)
696  {
697  /* Split ipaddr bits between network and subnet */
698  subnet_bitmask = (((Datum) 1) << subnet_size) - 1;
699  network = ipaddr_datum & ~subnet_bitmask;
700  }
701  else
702  {
703  /* Fit as many ipaddr bits as possible into network */
704  subnet_bitmask = 0;
705  network = ipaddr_datum;
706  }
707 
708 #if SIZEOF_DATUM == 8
709  if (ip_family(authoritative) == PGSQL_AF_INET)
710  {
711  /*
712  * IPv4 with 8 byte datums: keep all 32 netmasked bits, netmask size,
713  * and most significant 25 subnet bits
714  */
715  Datum netmask_size = (Datum) ip_bits(authoritative);
716  Datum subnet;
717 
718  /*
719  * Shift left 31 bits: 6 bits netmask size + 25 subnet bits.
720  *
721  * We don't make any distinction between network bits that are zero
722  * due to masking and "true"/non-masked zero bits. An abbreviated
723  * comparison that is resolved by comparing a non-masked and non-zero
724  * bit to a masked/zeroed bit is effectively resolved based on
725  * ip_bits(), even though the comparison won't reach the netmask_size
726  * bits.
727  */
728  network <<= (ABBREV_BITS_INET4_NETMASK_SIZE +
730 
731  /* Shift size to make room for subnet bits at the end */
732  netmask_size <<= ABBREV_BITS_INET4_SUBNET;
733 
734  /* Extract subnet bits without shifting them */
735  subnet = ipaddr_datum & subnet_bitmask;
736 
737  /*
738  * If we have more than 25 subnet bits, we can't fit everything. Shift
739  * subnet down to avoid clobbering bits that are only supposed to be
740  * used for netmask_size.
741  *
742  * Discarding the least significant subnet bits like this is correct
743  * because abbreviated comparisons that are resolved at the subnet
744  * level must have had equal netmask_size/ip_bits() values in order to
745  * get that far.
746  */
747  if (subnet_size > ABBREV_BITS_INET4_SUBNET)
748  subnet >>= subnet_size - ABBREV_BITS_INET4_SUBNET;
749 
750  /*
751  * Assemble the final abbreviated key without clobbering the ipfamily
752  * bit that must remain a zero.
753  */
754  res |= network | netmask_size | subnet;
755  }
756  else
757 #endif
758  {
759  /*
760  * 4 byte datums, or IPv6 with 8 byte datums: Use as many of the
761  * netmasked bits as will fit in final abbreviated key. Avoid
762  * clobbering the ipfamily bit that was set earlier.
763  */
764  res |= network >> 1;
765  }
766 
767  uss->input_count += 1;
768 
769  /* Hash abbreviated key */
770  if (uss->estimating)
771  {
772  uint32 tmp;
773 
774 #if SIZEOF_DATUM == 8
775  tmp = (uint32) res ^ (uint32) ((uint64) res >> 32);
776 #else /* SIZEOF_DATUM != 8 */
777  tmp = (uint32) res;
778 #endif
779 
781  }
782 
783  return res;
784 }
unsigned int uint32
Definition: c.h:506
static Datum hash_uint32(uint32 k)
Definition: hashfn.h:43
void addHyperLogLog(hyperLogLogState *cState, uint32 hash)
Definition: hyperloglog.c:167
#define ABBREV_BITS_INET4_SUBNET
Definition: network.c:43
#define ABBREV_BITS_INET4_NETMASK_SIZE
Definition: network.c:42
static uint32 pg_bswap32(uint32 x)
Definition: pg_bswap.h:64
#define BITS_PER_BYTE
static uint32 DatumGetUInt32(Datum X)
Definition: postgres.h:222
#define SIZEOF_DATUM
Definition: postgres.h:81
#define PGSQL_AF_INET6
Definition: inet.h:40

References network_sortsupport_state::abbr_card, ABBREV_BITS_INET4_NETMASK_SIZE, ABBREV_BITS_INET4_SUBNET, addHyperLogLog(), Assert, BITS_PER_BYTE, DatumGetInetPP(), DatumGetUInt32(), network_sortsupport_state::estimating, hash_uint32(), network_sortsupport_state::input_count, ip_addr, ip_bits, ip_family, ip_maxbits, pg_bswap32(), PGSQL_AF_INET, PGSQL_AF_INET6, res, SIZEOF_DATUM, and SortSupportData::ssup_extra.

Referenced by network_sortsupport().

◆ network_broadcast()

Datum network_broadcast ( PG_FUNCTION_ARGS  )

Definition at line 1279 of file network.c.

1280 {
1281  inet *ip = PG_GETARG_INET_PP(0);
1282  inet *dst;
1283  int byte;
1284  int bits;
1285  int maxbytes;
1286  unsigned char mask;
1287  unsigned char *a,
1288  *b;
1289 
1290  /* make sure any unused bits are zeroed */
1291  dst = (inet *) palloc0(sizeof(inet));
1292 
1293  maxbytes = ip_addrsize(ip);
1294  bits = ip_bits(ip);
1295  a = ip_addr(ip);
1296  b = ip_addr(dst);
1297 
1298  for (byte = 0; byte < maxbytes; byte++)
1299  {
1300  if (bits >= 8)
1301  {
1302  mask = 0x00;
1303  bits -= 8;
1304  }
1305  else if (bits == 0)
1306  mask = 0xff;
1307  else
1308  {
1309  mask = 0xff >> bits;
1310  bits = 0;
1311  }
1312 
1313  b[byte] = a[byte] | mask;
1314  }
1315 
1316  ip_family(dst) = ip_family(ip);
1317  ip_bits(dst) = ip_bits(ip);
1318  SET_INET_VARSIZE(dst);
1319 
1320  PG_RETURN_INET_P(dst);
1321 }

References a, b, ip_addr, ip_addrsize, ip_bits, ip_family, palloc0(), PG_GETARG_INET_PP, PG_RETURN_INET_P, and SET_INET_VARSIZE.

Referenced by network_scan_last().

◆ network_cmp()

Datum network_cmp ( PG_FUNCTION_ARGS  )

Definition at line 425 of file network.c.

426 {
427  inet *a1 = PG_GETARG_INET_PP(0);
428  inet *a2 = PG_GETARG_INET_PP(1);
429 
431 }
#define PG_RETURN_INT32(x)
Definition: fmgr.h:354
static int32 network_cmp_internal(inet *a1, inet *a2)
Definition: network.c:405

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_INT32.

◆ network_cmp_internal()

static int32 network_cmp_internal ( inet a1,
inet a2 
)
static

Definition at line 405 of file network.c.

406 {
407  if (ip_family(a1) == ip_family(a2))
408  {
409  int order;
410 
411  order = bitncmp(ip_addr(a1), ip_addr(a2),
412  Min(ip_bits(a1), ip_bits(a2)));
413  if (order != 0)
414  return order;
415  order = ((int) ip_bits(a1)) - ((int) ip_bits(a2));
416  if (order != 0)
417  return order;
418  return bitncmp(ip_addr(a1), ip_addr(a2), ip_maxbits(a1));
419  }
420 
421  return ip_family(a1) - ip_family(a2);
422 }
int bitncmp(const unsigned char *l, const unsigned char *r, int n)
Definition: network.c:1563

References a1, a2, bitncmp(), ip_addr, ip_bits, ip_family, ip_maxbits, and Min.

Referenced by network_cmp(), network_eq(), network_fast_cmp(), network_ge(), network_gt(), network_larger(), network_le(), network_lt(), network_ne(), and network_smaller().

◆ network_eq()

Datum network_eq ( PG_FUNCTION_ARGS  )

Definition at line 808 of file network.c.

809 {
810  inet *a1 = PG_GETARG_INET_PP(0);
811  inet *a2 = PG_GETARG_INET_PP(1);
812 
814 }

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_family()

Datum network_family ( PG_FUNCTION_ARGS  )

Definition at line 1260 of file network.c.

1261 {
1262  inet *ip = PG_GETARG_INET_PP(0);
1263 
1264  switch (ip_family(ip))
1265  {
1266  case PGSQL_AF_INET:
1267  PG_RETURN_INT32(4);
1268  break;
1269  case PGSQL_AF_INET6:
1270  PG_RETURN_INT32(6);
1271  break;
1272  default:
1273  PG_RETURN_INT32(0);
1274  break;
1275  }
1276 }

References ip_family, PG_GETARG_INET_PP, PG_RETURN_INT32, PGSQL_AF_INET, and PGSQL_AF_INET6.

◆ network_fast_cmp()

static int network_fast_cmp ( Datum  x,
Datum  y,
SortSupport  ssup 
)
static

Definition at line 473 of file network.c.

474 {
475  inet *arg1 = DatumGetInetPP(x);
476  inet *arg2 = DatumGetInetPP(y);
477 
478  return network_cmp_internal(arg1, arg2);
479 }
int y
Definition: isn.c:72

References DatumGetInetPP(), network_cmp_internal(), x, and y.

Referenced by network_sortsupport().

◆ network_ge()

Datum network_ge ( PG_FUNCTION_ARGS  )

Definition at line 817 of file network.c.

818 {
819  inet *a1 = PG_GETARG_INET_PP(0);
820  inet *a2 = PG_GETARG_INET_PP(1);
821 
823 }

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_gt()

Datum network_gt ( PG_FUNCTION_ARGS  )

Definition at line 826 of file network.c.

827 {
828  inet *a1 = PG_GETARG_INET_PP(0);
829  inet *a2 = PG_GETARG_INET_PP(1);
830 
832 }

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_host()

Datum network_host ( PG_FUNCTION_ARGS  )

Definition at line 1167 of file network.c.

1168 {
1169  inet *ip = PG_GETARG_INET_PP(0);
1170  char *ptr;
1171  char tmp[sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:255.255.255.255/128")];
1172 
1173  /* force display of max bits, regardless of masklen... */
1174  if (pg_inet_net_ntop(ip_family(ip), ip_addr(ip), ip_maxbits(ip),
1175  tmp, sizeof(tmp)) == NULL)
1176  ereport(ERROR,
1177  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
1178  errmsg("could not format inet value: %m")));
1179 
1180  /* Suppress /n if present (shouldn't happen now) */
1181  if ((ptr = strchr(tmp, '/')) != NULL)
1182  *ptr = '\0';
1183 
1185 }

References cstring_to_text(), ereport, errcode(), errmsg(), ERROR, ip_addr, ip_family, ip_maxbits, PG_GETARG_INET_PP, pg_inet_net_ntop(), and PG_RETURN_TEXT_P.

◆ network_hostmask()

Datum network_hostmask ( PG_FUNCTION_ARGS  )

Definition at line 1410 of file network.c.

1411 {
1412  inet *ip = PG_GETARG_INET_PP(0);
1413  inet *dst;
1414  int byte;
1415  int bits;
1416  int maxbytes;
1417  unsigned char mask;
1418  unsigned char *b;
1419 
1420  /* make sure any unused bits are zeroed */
1421  dst = (inet *) palloc0(sizeof(inet));
1422 
1423  maxbytes = ip_addrsize(ip);
1424  bits = ip_maxbits(ip) - ip_bits(ip);
1425  b = ip_addr(dst);
1426 
1427  byte = maxbytes - 1;
1428 
1429  while (bits)
1430  {
1431  if (bits >= 8)
1432  {
1433  mask = 0xff;
1434  bits -= 8;
1435  }
1436  else
1437  {
1438  mask = 0xff >> (8 - bits);
1439  bits = 0;
1440  }
1441 
1442  b[byte] = mask;
1443  byte--;
1444  }
1445 
1446  ip_family(dst) = ip_family(ip);
1447  ip_bits(dst) = ip_maxbits(ip);
1448  SET_INET_VARSIZE(dst);
1449 
1450  PG_RETURN_INET_P(dst);
1451 }

References b, ip_addr, ip_addrsize, ip_bits, ip_family, ip_maxbits, palloc0(), PG_GETARG_INET_PP, PG_RETURN_INET_P, and SET_INET_VARSIZE.

◆ network_in()

static inet* network_in ( char *  src,
bool  is_cidr,
Node escontext 
)
static

Definition at line 75 of file network.c.

76 {
77  int bits;
78  inet *dst;
79 
80  dst = (inet *) palloc0(sizeof(inet));
81 
82  /*
83  * First, check to see if this is an IPv6 or IPv4 address. IPv6 addresses
84  * will have a : somewhere in them (several, in fact) so if there is one
85  * present, assume it's V6, otherwise assume it's V4.
86  */
87 
88  if (strchr(src, ':') != NULL)
90  else
91  ip_family(dst) = PGSQL_AF_INET;
92 
93  bits = pg_inet_net_pton(ip_family(dst), src, ip_addr(dst),
94  is_cidr ? ip_addrsize(dst) : -1);
95  if ((bits < 0) || (bits > ip_maxbits(dst)))
96  ereturn(escontext, NULL,
97  (errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
98  /* translator: first %s is inet or cidr */
99  errmsg("invalid input syntax for type %s: \"%s\"",
100  is_cidr ? "cidr" : "inet", src)));
101 
102  /*
103  * Error check: CIDR values must not have any bits set beyond the masklen.
104  */
105  if (is_cidr)
106  {
107  if (!addressOK(ip_addr(dst), bits, ip_family(dst)))
108  ereturn(escontext, NULL,
109  (errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
110  errmsg("invalid cidr value: \"%s\"", src),
111  errdetail("Value has bits set to right of mask.")));
112  }
113 
114  ip_bits(dst) = bits;
115  SET_INET_VARSIZE(dst);
116 
117  return dst;
118 }
int errdetail(const char *fmt,...)
Definition: elog.c:1203
#define ereturn(context, dummy_value,...)
Definition: elog.h:277
int pg_inet_net_pton(int af, const char *src, void *dst, size_t size)
Definition: inet_net_pton.c:62
static bool addressOK(unsigned char *a, int bits, int family)
Definition: network.c:1635

References addressOK(), ereturn, errcode(), errdetail(), errmsg(), ip_addr, ip_addrsize, ip_bits, ip_family, ip_maxbits, palloc0(), pg_inet_net_pton(), PGSQL_AF_INET, PGSQL_AF_INET6, and SET_INET_VARSIZE.

Referenced by cidr_in(), inet_client_addr(), inet_in(), and inet_server_addr().

◆ network_larger()

Datum network_larger ( PG_FUNCTION_ARGS  )

Definition at line 859 of file network.c.

860 {
861  inet *a1 = PG_GETARG_INET_PP(0);
862  inet *a2 = PG_GETARG_INET_PP(1);
863 
864  if (network_cmp_internal(a1, a2) > 0)
866  else
868 }

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_INET_P.

◆ network_le()

Datum network_le ( PG_FUNCTION_ARGS  )

Definition at line 799 of file network.c.

800 {
801  inet *a1 = PG_GETARG_INET_PP(0);
802  inet *a2 = PG_GETARG_INET_PP(1);
803 
805 }

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_lt()

Datum network_lt ( PG_FUNCTION_ARGS  )

Definition at line 790 of file network.c.

791 {
792  inet *a1 = PG_GETARG_INET_PP(0);
793  inet *a2 = PG_GETARG_INET_PP(1);
794 
796 }

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_masklen()

Datum network_masklen ( PG_FUNCTION_ARGS  )

Definition at line 1252 of file network.c.

1253 {
1254  inet *ip = PG_GETARG_INET_PP(0);
1255 
1256  PG_RETURN_INT32(ip_bits(ip));
1257 }

References ip_bits, PG_GETARG_INET_PP, and PG_RETURN_INT32.

◆ network_ne()

Datum network_ne ( PG_FUNCTION_ARGS  )

Definition at line 835 of file network.c.

836 {
837  inet *a1 = PG_GETARG_INET_PP(0);
838  inet *a2 = PG_GETARG_INET_PP(1);
839 
841 }

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_netmask()

Datum network_netmask ( PG_FUNCTION_ARGS  )

Definition at line 1368 of file network.c.

1369 {
1370  inet *ip = PG_GETARG_INET_PP(0);
1371  inet *dst;
1372  int byte;
1373  int bits;
1374  unsigned char mask;
1375  unsigned char *b;
1376 
1377  /* make sure any unused bits are zeroed */
1378  dst = (inet *) palloc0(sizeof(inet));
1379 
1380  bits = ip_bits(ip);
1381  b = ip_addr(dst);
1382 
1383  byte = 0;
1384 
1385  while (bits)
1386  {
1387  if (bits >= 8)
1388  {
1389  mask = 0xff;
1390  bits -= 8;
1391  }
1392  else
1393  {
1394  mask = 0xff << (8 - bits);
1395  bits = 0;
1396  }
1397 
1398  b[byte] = mask;
1399  byte++;
1400  }
1401 
1402  ip_family(dst) = ip_family(ip);
1403  ip_bits(dst) = ip_maxbits(ip);
1404  SET_INET_VARSIZE(dst);
1405 
1406  PG_RETURN_INET_P(dst);
1407 }

References b, ip_addr, ip_bits, ip_family, ip_maxbits, palloc0(), PG_GETARG_INET_PP, PG_RETURN_INET_P, and SET_INET_VARSIZE.

◆ network_network()

Datum network_network ( PG_FUNCTION_ARGS  )

Definition at line 1324 of file network.c.

1325 {
1326  inet *ip = PG_GETARG_INET_PP(0);
1327  inet *dst;
1328  int byte;
1329  int bits;
1330  unsigned char mask;
1331  unsigned char *a,
1332  *b;
1333 
1334  /* make sure any unused bits are zeroed */
1335  dst = (inet *) palloc0(sizeof(inet));
1336 
1337  bits = ip_bits(ip);
1338  a = ip_addr(ip);
1339  b = ip_addr(dst);
1340 
1341  byte = 0;
1342 
1343  while (bits)
1344  {
1345  if (bits >= 8)
1346  {
1347  mask = 0xff;
1348  bits -= 8;
1349  }
1350  else
1351  {
1352  mask = 0xff << (8 - bits);
1353  bits = 0;
1354  }
1355 
1356  b[byte] = a[byte] & mask;
1357  byte++;
1358  }
1359 
1360  ip_family(dst) = ip_family(ip);
1361  ip_bits(dst) = ip_bits(ip);
1362  SET_INET_VARSIZE(dst);
1363 
1364  PG_RETURN_INET_P(dst);
1365 }

References a, b, ip_addr, ip_bits, ip_family, palloc0(), PG_GETARG_INET_PP, PG_RETURN_INET_P, and SET_INET_VARSIZE.

Referenced by network_scan_first().

◆ network_out()

static char* network_out ( inet src,
bool  is_cidr 
)
static

Definition at line 141 of file network.c.

142 {
143  char tmp[sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:255.255.255.255/128")];
144  char *dst;
145  int len;
146 
147  dst = pg_inet_net_ntop(ip_family(src), ip_addr(src), ip_bits(src),
148  tmp, sizeof(tmp));
149  if (dst == NULL)
150  ereport(ERROR,
151  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
152  errmsg("could not format inet value: %m")));
153 
154  /* For CIDR, add /n if not present */
155  if (is_cidr && strchr(tmp, '/') == NULL)
156  {
157  len = strlen(tmp);
158  snprintf(tmp + len, sizeof(tmp) - len, "/%u", ip_bits(src));
159  }
160 
161  return pstrdup(tmp);
162 }
char * pstrdup(const char *in)
Definition: mcxt.c:1696
#define snprintf
Definition: port.h:238

References ereport, errcode(), errmsg(), ERROR, ip_addr, ip_bits, ip_family, len, pg_inet_net_ntop(), pstrdup(), and snprintf.

Referenced by cidr_out(), and inet_out().

◆ network_overlap()

Datum network_overlap ( PG_FUNCTION_ARGS  )

Definition at line 957 of file network.c.

958 {
959  inet *a1 = PG_GETARG_INET_PP(0);
960  inet *a2 = PG_GETARG_INET_PP(1);
961 
962  if (ip_family(a1) == ip_family(a2))
963  {
965  Min(ip_bits(a1), ip_bits(a2))) == 0);
966  }
967 
968  PG_RETURN_BOOL(false);
969 }

References a1, a2, bitncmp(), ip_addr, ip_bits, ip_family, Min, PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_recv()

static inet* network_recv ( StringInfo  buf,
bool  is_cidr 
)
static

Definition at line 192 of file network.c.

193 {
194  inet *addr;
195  char *addrptr;
196  int bits;
197  int nb,
198  i;
199 
200  /* make sure any unused bits in a CIDR value are zeroed */
201  addr = (inet *) palloc0(sizeof(inet));
202 
203  ip_family(addr) = pq_getmsgbyte(buf);
204  if (ip_family(addr) != PGSQL_AF_INET &&
205  ip_family(addr) != PGSQL_AF_INET6)
206  ereport(ERROR,
207  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
208  /* translator: %s is inet or cidr */
209  errmsg("invalid address family in external \"%s\" value",
210  is_cidr ? "cidr" : "inet")));
211  bits = pq_getmsgbyte(buf);
212  if (bits < 0 || bits > ip_maxbits(addr))
213  ereport(ERROR,
214  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
215  /* translator: %s is inet or cidr */
216  errmsg("invalid bits in external \"%s\" value",
217  is_cidr ? "cidr" : "inet")));
218  ip_bits(addr) = bits;
219  i = pq_getmsgbyte(buf); /* ignore is_cidr */
220  nb = pq_getmsgbyte(buf);
221  if (nb != ip_addrsize(addr))
222  ereport(ERROR,
223  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
224  /* translator: %s is inet or cidr */
225  errmsg("invalid length in external \"%s\" value",
226  is_cidr ? "cidr" : "inet")));
227 
228  addrptr = (char *) ip_addr(addr);
229  for (i = 0; i < nb; i++)
230  addrptr[i] = pq_getmsgbyte(buf);
231 
232  /*
233  * Error check: CIDR values must not have any bits set beyond the masklen.
234  */
235  if (is_cidr)
236  {
237  if (!addressOK(ip_addr(addr), bits, ip_family(addr)))
238  ereport(ERROR,
239  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
240  errmsg("invalid external \"cidr\" value"),
241  errdetail("Value has bits set to right of mask.")));
242  }
243 
244  SET_INET_VARSIZE(addr);
245 
246  return addr;
247 }
int pq_getmsgbyte(StringInfo msg)
Definition: pqformat.c:399

References addressOK(), buf, ereport, errcode(), errdetail(), errmsg(), ERROR, i, ip_addr, ip_addrsize, ip_bits, ip_family, ip_maxbits, palloc0(), PGSQL_AF_INET, PGSQL_AF_INET6, pq_getmsgbyte(), and SET_INET_VARSIZE.

Referenced by cidr_recv(), and inet_recv().

◆ network_scan_first()

Datum network_scan_first ( Datum  in)

Definition at line 1684 of file network.c.

1685 {
1687 }
Datum network_network(PG_FUNCTION_ARGS)
Definition: network.c:1324

References DirectFunctionCall1, and network_network().

Referenced by match_network_subset().

◆ network_scan_last()

Datum network_scan_last ( Datum  in)

Definition at line 1698 of file network.c.

1699 {
1702  Int32GetDatum(-1));
1703 }
#define DirectFunctionCall2(func, arg1, arg2)
Definition: fmgr.h:643
Datum network_broadcast(PG_FUNCTION_ARGS)
Definition: network.c:1279
Datum inet_set_masklen(PG_FUNCTION_ARGS)
Definition: network.c:324
static Datum Int32GetDatum(int32 X)
Definition: postgres.h:212

References DirectFunctionCall1, DirectFunctionCall2, inet_set_masklen(), Int32GetDatum(), and network_broadcast().

Referenced by match_network_subset().

◆ network_send()

static bytea* network_send ( inet addr,
bool  is_cidr 
)
static

Definition at line 270 of file network.c.

271 {
273  char *addrptr;
274  int nb,
275  i;
276 
278  pq_sendbyte(&buf, ip_family(addr));
279  pq_sendbyte(&buf, ip_bits(addr));
280  pq_sendbyte(&buf, is_cidr);
281  nb = ip_addrsize(addr);
282  if (nb < 0)
283  nb = 0;
284  pq_sendbyte(&buf, nb);
285  addrptr = (char *) ip_addr(addr);
286  for (i = 0; i < nb; i++)
287  pq_sendbyte(&buf, addrptr[i]);
288  return pq_endtypsend(&buf);
289 }
void pq_begintypsend(StringInfo buf)
Definition: pqformat.c:326
bytea * pq_endtypsend(StringInfo buf)
Definition: pqformat.c:346
static void pq_sendbyte(StringInfo buf, uint8 byt)
Definition: pqformat.h:160

References buf, i, ip_addr, ip_addrsize, ip_bits, ip_family, pq_begintypsend(), pq_endtypsend(), and pq_sendbyte().

Referenced by cidr_send(), and inet_send().

◆ network_show()

Datum network_show ( PG_FUNCTION_ARGS  )

Definition at line 1193 of file network.c.

1194 {
1195  inet *ip = PG_GETARG_INET_PP(0);
1196  int len;
1197  char tmp[sizeof("xxxx:xxxx:xxxx:xxxx:xxxx:xxxx:255.255.255.255/128")];
1198 
1199  if (pg_inet_net_ntop(ip_family(ip), ip_addr(ip), ip_maxbits(ip),
1200  tmp, sizeof(tmp)) == NULL)
1201  ereport(ERROR,
1202  (errcode(ERRCODE_INVALID_BINARY_REPRESENTATION),
1203  errmsg("could not format inet value: %m")));
1204 
1205  /* Add /n if not present (which it won't be) */
1206  if (strchr(tmp, '/') == NULL)
1207  {
1208  len = strlen(tmp);
1209  snprintf(tmp + len, sizeof(tmp) - len, "/%u", ip_bits(ip));
1210  }
1211 
1213 }

References cstring_to_text(), ereport, errcode(), errmsg(), ERROR, ip_addr, ip_bits, ip_family, ip_maxbits, len, PG_GETARG_INET_PP, pg_inet_net_ntop(), PG_RETURN_TEXT_P, and snprintf.

◆ network_smaller()

Datum network_smaller ( PG_FUNCTION_ARGS  )

Definition at line 847 of file network.c.

848 {
849  inet *a1 = PG_GETARG_INET_PP(0);
850  inet *a2 = PG_GETARG_INET_PP(1);
851 
852  if (network_cmp_internal(a1, a2) < 0)
854  else
856 }

References a1, a2, network_cmp_internal(), PG_GETARG_INET_PP, and PG_RETURN_INET_P.

◆ network_sortsupport()

Datum network_sortsupport ( PG_FUNCTION_ARGS  )

Definition at line 437 of file network.c.

438 {
440 
442  ssup->ssup_extra = NULL;
443 
444  if (ssup->abbreviate)
445  {
447  MemoryContext oldcontext;
448 
449  oldcontext = MemoryContextSwitchTo(ssup->ssup_cxt);
450 
451  uss = palloc(sizeof(network_sortsupport_state));
452  uss->input_count = 0;
453  uss->estimating = true;
454  initHyperLogLog(&uss->abbr_card, 10);
455 
456  ssup->ssup_extra = uss;
457 
462 
463  MemoryContextSwitchTo(oldcontext);
464  }
465 
466  PG_RETURN_VOID();
467 }
#define PG_RETURN_VOID()
Definition: fmgr.h:349
void initHyperLogLog(hyperLogLogState *cState, uint8 bwidth)
Definition: hyperloglog.c:66
static int network_fast_cmp(Datum x, Datum y, SortSupport ssup)
Definition: network.c:473
static Datum network_abbrev_convert(Datum original, SortSupport ssup)
Definition: network.c:619
static bool network_abbrev_abort(int memtupcount, SortSupport ssup)
Definition: network.c:488
MemoryContextSwitchTo(old_ctx)
struct SortSupportData * SortSupport
Definition: sortsupport.h:58
int(* comparator)(Datum x, Datum y, SortSupport ssup)
Definition: sortsupport.h:106
Datum(* abbrev_converter)(Datum original, SortSupport ssup)
Definition: sortsupport.h:172
MemoryContext ssup_cxt
Definition: sortsupport.h:66
int(* abbrev_full_comparator)(Datum x, Datum y, SortSupport ssup)
Definition: sortsupport.h:191
bool(* abbrev_abort)(int memtupcount, SortSupport ssup)
Definition: sortsupport.h:182
int ssup_datum_unsigned_cmp(Datum x, Datum y, SortSupport ssup)
Definition: tuplesort.c:3139

References network_sortsupport_state::abbr_card, SortSupportData::abbrev_abort, SortSupportData::abbrev_converter, SortSupportData::abbrev_full_comparator, SortSupportData::abbreviate, SortSupportData::comparator, network_sortsupport_state::estimating, initHyperLogLog(), network_sortsupport_state::input_count, MemoryContextSwitchTo(), network_abbrev_abort(), network_abbrev_convert(), network_fast_cmp(), palloc(), PG_GETARG_POINTER, PG_RETURN_VOID, SortSupportData::ssup_cxt, ssup_datum_unsigned_cmp(), and SortSupportData::ssup_extra.

◆ network_sub()

Datum network_sub ( PG_FUNCTION_ARGS  )

Definition at line 897 of file network.c.

898 {
899  inet *a1 = PG_GETARG_INET_PP(0);
900  inet *a2 = PG_GETARG_INET_PP(1);
901 
902  if (ip_family(a1) == ip_family(a2))
903  {
905  bitncmp(ip_addr(a1), ip_addr(a2), ip_bits(a2)) == 0);
906  }
907 
908  PG_RETURN_BOOL(false);
909 }

References a1, a2, bitncmp(), ip_addr, ip_bits, ip_family, PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_subeq()

Datum network_subeq ( PG_FUNCTION_ARGS  )

Definition at line 912 of file network.c.

913 {
914  inet *a1 = PG_GETARG_INET_PP(0);
915  inet *a2 = PG_GETARG_INET_PP(1);
916 
917  if (ip_family(a1) == ip_family(a2))
918  {
920  bitncmp(ip_addr(a1), ip_addr(a2), ip_bits(a2)) == 0);
921  }
922 
923  PG_RETURN_BOOL(false);
924 }

References a1, a2, bitncmp(), ip_addr, ip_bits, ip_family, PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_subset_support()

Datum network_subset_support ( PG_FUNCTION_ARGS  )

Definition at line 975 of file network.c.

976 {
977  Node *rawreq = (Node *) PG_GETARG_POINTER(0);
978  Node *ret = NULL;
979 
980  if (IsA(rawreq, SupportRequestIndexCondition))
981  {
982  /* Try to convert operator/function call to index conditions */
984 
985  if (is_opclause(req->node))
986  {
987  OpExpr *clause = (OpExpr *) req->node;
988 
989  Assert(list_length(clause->args) == 2);
990  ret = (Node *)
992  (Node *) lsecond(clause->args),
993  req->indexarg,
994  req->funcid,
995  req->opfamily);
996  }
997  else if (is_funcclause(req->node)) /* be paranoid */
998  {
999  FuncExpr *clause = (FuncExpr *) req->node;
1000 
1001  Assert(list_length(clause->args) == 2);
1002  ret = (Node *)
1004  (Node *) lsecond(clause->args),
1005  req->indexarg,
1006  req->funcid,
1007  req->opfamily);
1008  }
1009  }
1010 
1011  PG_RETURN_POINTER(ret);
1012 }
#define PG_RETURN_POINTER(x)
Definition: fmgr.h:361
static List * match_network_function(Node *leftop, Node *rightop, int indexarg, Oid funcid, Oid opfamily)
Definition: network.c:1022
static bool is_opclause(const void *clause)
Definition: nodeFuncs.h:76
static bool is_funcclause(const void *clause)
Definition: nodeFuncs.h:69
static int list_length(const List *l)
Definition: pg_list.h:152
#define linitial(l)
Definition: pg_list.h:178
#define lsecond(l)
Definition: pg_list.h:183
List * args
Definition: primnodes.h:768
Definition: nodes.h:129
List * args
Definition: primnodes.h:836

References FuncExpr::args, OpExpr::args, Assert, SupportRequestIndexCondition::funcid, SupportRequestIndexCondition::indexarg, is_funcclause(), is_opclause(), IsA, linitial, list_length(), lsecond, match_network_function(), SupportRequestIndexCondition::node, SupportRequestIndexCondition::opfamily, PG_GETARG_POINTER, and PG_RETURN_POINTER.

◆ network_sup()

Datum network_sup ( PG_FUNCTION_ARGS  )

Definition at line 927 of file network.c.

928 {
929  inet *a1 = PG_GETARG_INET_PP(0);
930  inet *a2 = PG_GETARG_INET_PP(1);
931 
932  if (ip_family(a1) == ip_family(a2))
933  {
935  bitncmp(ip_addr(a1), ip_addr(a2), ip_bits(a1)) == 0);
936  }
937 
938  PG_RETURN_BOOL(false);
939 }

References a1, a2, bitncmp(), ip_addr, ip_bits, ip_family, PG_GETARG_INET_PP, and PG_RETURN_BOOL.

◆ network_supeq()

Datum network_supeq ( PG_FUNCTION_ARGS  )

Definition at line 942 of file network.c.

943 {
944  inet *a1 = PG_GETARG_INET_PP(0);
945  inet *a2 = PG_GETARG_INET_PP(1);
946 
947  if (ip_family(a1) == ip_family(a2))
948  {
950  bitncmp(ip_addr(a1), ip_addr(a2), ip_bits(a1)) == 0);
951  }
952 
953  PG_RETURN_BOOL(false);
954 }

References a1, a2, bitncmp(), ip_addr, ip_bits, ip_family, PG_GETARG_INET_PP, and PG_RETURN_BOOL.