@@ -15,6 +15,7 @@ DEF PGSQL_AF_INET6 = 3 # AF_INET + 1
15
15
16
16
17
17
_ipaddr = ipaddress.ip_address
18
+ _ipiface = ipaddress.ip_interface
18
19
_ipnet = ipaddress.ip_network
19
20
20
21
@@ -59,15 +60,19 @@ cdef inline _net_encode(WriteBuffer buf, int8_t family, uint32_t bits,
59
60
buf.write_cstr(addrbytes, addrlen)
60
61
61
62
62
- cdef net_decode(CodecContext settings, FRBuffer * buf):
63
+ cdef net_decode(CodecContext settings, FRBuffer * buf, bint as_cidr ):
63
64
cdef:
64
65
int32_t family = < int32_t> frb_read(buf, 1 )[0 ]
65
66
uint8_t bits = < uint8_t> frb_read(buf, 1 )[0 ]
67
+ int prefix_len
66
68
int32_t is_cidr = < int32_t> frb_read(buf, 1 )[0 ]
67
69
int32_t addrlen = < int32_t> frb_read(buf, 1 )[0 ]
68
70
bytes addr
69
71
uint8_t max_prefix_len = _ip_max_prefix_len(family)
70
72
73
+ if is_cidr != as_cidr:
74
+ raise ValueError (' unexpected CIDR flag set in non-cidr value' )
75
+
71
76
if family != PGSQL_AF_INET and family != PGSQL_AF_INET6:
72
77
raise ValueError (' invalid address family in "{}" value' .format(
73
78
' cidr' if is_cidr else ' inet'
@@ -87,8 +92,13 @@ cdef net_decode(CodecContext settings, FRBuffer *buf):
87
92
88
93
addr = cpython.PyBytes_FromStringAndSize(frb_read(buf, addrlen), addrlen)
89
94
90
- if is_cidr or bits != max_prefix_len:
91
- return _ipnet(addr).supernet(new_prefix = cpython.PyLong_FromLong(bits))
95
+ if as_cidr or bits != max_prefix_len:
96
+ prefix_len = cpython.PyLong_FromLong(bits)
97
+
98
+ if as_cidr:
99
+ return _ipnet((addr, prefix_len))
100
+ else :
101
+ return _ipiface((addr, prefix_len))
92
102
else :
93
103
return _ipaddr(addr)
94
104
@@ -103,6 +113,10 @@ cdef cidr_encode(CodecContext settings, WriteBuffer buf, obj):
103
113
_net_encode(buf, family, ipnet.prefixlen, 1 , ipnet.network_address.packed)
104
114
105
115
116
+ cdef cidr_decode(CodecContext settings, FRBuffer * buf):
117
+ return net_decode(settings, buf, True )
118
+
119
+
106
120
cdef inet_encode(CodecContext settings, WriteBuffer buf, obj):
107
121
cdef:
108
122
object ipaddr
@@ -113,7 +127,13 @@ cdef inet_encode(CodecContext settings, WriteBuffer buf, obj):
113
127
except ValueError :
114
128
# PostgreSQL accepts *both* CIDR and host values
115
129
# for the host datatype.
116
- cidr_encode(settings, buf, obj)
130
+ ipaddr = _ipiface(obj)
131
+ family = _ver_to_family(ipaddr.version)
132
+ _net_encode(buf, family, ipaddr.network.prefixlen, 1 , ipaddr.packed)
117
133
else :
118
134
family = _ver_to_family(ipaddr.version)
119
135
_net_encode(buf, family, _ip_max_prefix_len(family), 0 , ipaddr.packed)
136
+
137
+
138
+ cdef inet_decode(CodecContext settings, FRBuffer * buf):
139
+ return net_decode(settings, buf, False )
0 commit comments