Skip to content

Commit

Permalink
Merge pull request #648 from LiZhenCheng9527/rbac-fix
Browse files Browse the repository at this point in the history
Fixed bug in bpf where IPv4 destination address was stored as IPv6
  • Loading branch information
kmesh-bot authored Aug 1, 2024
2 parents 75a7312 + ccb0848 commit 9c10c28
Show file tree
Hide file tree
Showing 4 changed files with 28 additions and 7 deletions.
24 changes: 20 additions & 4 deletions bpf/kmesh/workload/sockops.c
Original file line number Diff line number Diff line change
Expand Up @@ -38,8 +38,12 @@ static inline bool is_managed_by_kmesh(struct bpf_sock_ops *skops)
struct manager_key key = {0};
if (skops->family == AF_INET)
key.addr.ip4 = skops->local_ip4;
if (skops->family == AF_INET6)
IP6_COPY(key.addr.ip6, skops->local_ip6);
if (skops->family == AF_INET6) {
if (is_ipv4_mapped_addr(skops->local_ip6))
key.addr.ip4 = skops->local_ip6[3];
else
IP6_COPY(key.addr.ip6, skops->local_ip6);
}

int *value = bpf_map_lookup_elem(&map_of_manager, &key);
if (!value)
Expand All @@ -56,7 +60,8 @@ static inline void extract_skops_to_tuple(struct bpf_sock_ops *skops, struct bpf
tuple_key->ipv4.sport = bpf_htons(GET_SKOPS_LOCAL_PORT(skops));
// remote_port is network byteorder
tuple_key->ipv4.dport = GET_SKOPS_REMOTE_PORT(skops);
} else {
}
if (skops->family == AF_INET6) {
bpf_memcpy(tuple_key->ipv6.saddr, skops->local_ip6, IPV6_ADDR_LEN);
bpf_memcpy(tuple_key->ipv6.daddr, skops->remote_ip6, IPV6_ADDR_LEN);
// local_port is host byteorder, need to htons
Expand All @@ -75,14 +80,22 @@ static inline void extract_skops_to_tuple_reverse(struct bpf_sock_ops *skops, st
tuple_key->ipv4.sport = GET_SKOPS_REMOTE_PORT(skops);
// local_port is host byteorder
tuple_key->ipv4.dport = bpf_htons(GET_SKOPS_LOCAL_PORT(skops));
} else {
}
if (skops->family == AF_INET6) {
bpf_memcpy(tuple_key->ipv6.saddr, skops->remote_ip6, IPV6_ADDR_LEN);
bpf_memcpy(tuple_key->ipv6.daddr, skops->local_ip6, IPV6_ADDR_LEN);
// remote_port is network byteorder
tuple_key->ipv6.sport = GET_SKOPS_REMOTE_PORT(skops);
// local_port is host byteorder
tuple_key->ipv6.dport = bpf_htons(GET_SKOPS_LOCAL_PORT(skops));
}

if (is_ipv4_mapped_addr(tuple_key->ipv6.daddr) || is_ipv4_mapped_addr(tuple_key->ipv6.saddr)) {
tuple_key->ipv4.saddr = tuple_key->ipv6.saddr[3];
tuple_key->ipv4.daddr = tuple_key->ipv6.daddr[3];
tuple_key->ipv4.sport = tuple_key->ipv6.sport;
tuple_key->ipv4.dport = tuple_key->ipv6.dport;
}
}

// clean map_of_auth
Expand Down Expand Up @@ -123,6 +136,9 @@ static inline void auth_ip_tuple(struct bpf_sock_ops *skops)
// In this way, auth can be performed normally.
extract_skops_to_tuple_reverse(skops, &(*msg).tuple);
(*msg).type = (skops->family == AF_INET) ? IPV4 : IPV6;
if (is_ipv4_mapped_addr(skops->local_ip6)) {
(*msg).type = IPV4;
}
bpf_ringbuf_submit(msg, 0);
}

Expand Down
1 change: 0 additions & 1 deletion bpf/kmesh/workload/xdp.c
Original file line number Diff line number Diff line change
Expand Up @@ -117,7 +117,6 @@ int xdp_shutdown(struct xdp_md *ctx)

if (parser_xdp_info(ctx, &info) == PARSER_FAILED)
return XDP_PASS;

if (info.iph->version != 4 && info.iph->version != 6)
return XDP_PASS;

Expand Down
7 changes: 6 additions & 1 deletion pkg/auth/rbac.go
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,7 @@ func (r *Rbac) doRbac(conn *rbacConnection) bool {
dstWorkload := r.workloadCache.GetWorkloadByAddr(networkAddress)
// If no workload found, deny
if dstWorkload == nil {
log.Warnf("Auth denied for connection: %v because destination workload not found", conn.dstIp)
return false
}

Expand All @@ -189,6 +190,7 @@ func (r *Rbac) doRbac(conn *rbacConnection) bool {
// 1. If there is ANY deny policy, deny the request
for _, denyPolicy := range denyPolicies {
if matches(conn, denyPolicy) {
log.Infof("Auth denied for connection: %+v because authorization policy", conn)
return false
}
}
Expand Down Expand Up @@ -480,7 +482,10 @@ func (r *Rbac) buildConnV6(buf *bytes.Buffer) (rbacConnection, error) {
conn.dstIp = binary.BigEndian.AppendUint32(conn.dstIp, tupleV6.DstAddr[i])
}
conn.dstPort = uint32(tupleV6.DstPort)
// conn.dstIp = restoreIPv4(conn.dstIp)
// conn.srcIp = restoreIPv4(conn.srcIp)
conn.srcIdentity = r.getIdentityByIp(conn.srcIp)

return conn, nil
}

Expand All @@ -496,7 +501,7 @@ func isEmptyMatch(m *security.Match) bool {
m.GetNamespaces() == nil && m.GetNotNamespaces() == nil
}

// todo : get identity form tls connection
// todo : get identity from tls connection
func (r *Rbac) getIdentityByIp(ip []byte) Identity {
var networkAddress cache.NetworkAddress
networkAddress.Address, _ = netip.AddrFromSlice(ip)
Expand Down
3 changes: 2 additions & 1 deletion pkg/auth/rbac_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2149,7 +2149,7 @@ func TestRbac_Run(t *testing.T) {
Uid: "123456",
Addresses: [][]byte{
{192, 168, 120, 1},
net.ParseIP("fd80::1"),
net.ParseIP("0:1::fd80:0"),
},
AuthorizationPolicies: []string{DENY_AUTH},
})
Expand All @@ -2163,6 +2163,7 @@ func TestRbac_Run(t *testing.T) {
"1. IPv4: Deny, records found in map_of_auth",
args{
msgType: MSG_TYPE_IPV4,
// 192, 168, 120, 1, 192, 168, 122, 3, , , 8080
lookupKey: append([]byte{0xC0, 0xA8, 0x78, 0x01, 0xC0, 0xA8, 0x7A, 0x03, 0xC2, 0x6C, 0x1F, 0x90},
make([]byte, TUPLE_LEN-IPV4_TUPLE_LENGTH)...),
},
Expand Down

0 comments on commit 9c10c28

Please sign in to comment.