以下是用户层通过XFRM_MSG_GETSA获取全部SA的C代码:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <fcntl.h>
#include <sys/socket.h>
#include <linux/xfrm.h>

#define BUFFER_SIZE 4096

int main() {
    int sock_fd = socket(PF_NETLINK, SOCK_RAW, NETLINK_XFRM);
    if (sock_fd < 0) {
        perror("socket");
        exit(1);
    }

    struct sockaddr_nl src_addr = {
        .nl_family = AF_NETLINK,
        .nl_pid = getpid(),
        .nl_groups = 0
    };
    if (bind(sock_fd, (struct sockaddr*)&src_addr, sizeof(src_addr)) < 0) {
        perror("bind");
        exit(1);
    }

    struct sockaddr_nl dst_addr = {
        .nl_family = AF_NETLINK,
        .nl_pid = 0,
        .nl_groups = 0
    };

    struct {
        struct nlmsghdr nlh;
        struct xfrm_userpolicy_info info;
    } req = {
        .nlh = {
            .nlmsg_len = NLMSG_LENGTH(sizeof(struct xfrm_userpolicy_info)),
            .nlmsg_type = XFRM_MSG_GETPOLICY,
            .nlmsg_flags = NLM_F_REQUEST | NLM_F_DUMP,
            .nlmsg_seq = 0,
            .nlmsg_pid = getpid()
        },
        .info = {
            .pol_family = AF_INET6
        }
    };

    if (sendto(sock_fd, &req, req.nlh.nlmsg_len, 0, (struct sockaddr*)&dst_addr, sizeof(dst_addr)) < 0) {
        perror("sendto");
        exit(1);
    }

    char buffer[BUFFER_SIZE];
    struct iovec iov = {
        .iov_base = buffer,
        .iov_len = sizeof(buffer)
    };
    struct msghdr msg = {
        .msg_name = &dst_addr,
        .msg_namelen = sizeof(dst_addr),
        .msg_iov = &iov,
        .msg_iovlen = 1
    };

    ssize_t n = recvmsg(sock_fd, &msg, 0);
    if (n < 0) {
        perror("recvmsg");
        exit(1);
    }

    for (struct nlmsghdr* nlh = (struct nlmsghdr*)buffer; NLMSG_OK(nlh, n); nlh = NLMSG_NEXT(nlh, n)) {
        if (nlh->nlmsg_type == NLMSG_ERROR || nlh->nlmsg_type == NLMSG_DONE) {
            break;
        }

        struct xfrm_userpolicy_info* info = (struct xfrm_userpolicy_info*)NLMSG_DATA(nlh);

        printf("Policy:\n");
        printf("  Family: %u\n", info->pol_family);
        printf("  Type: %u\n", info->pol_type);
        printf("  Dir: %u\n", info->pol_dir);
        printf("  Priority: %u\n", info->priority);
        printf("  Index: %u\n", info->index);
        printf("  Refcount: %u\n", info->refcnt);
        printf("  Flags: %u\n", info->flags);
        printf("  Share: %u\n", info->share);
        printf("  Action: %u\n", info->action);
        printf("  Sel:\n");
        printf("    Family: %u\n", info->sel.family);
        printf("    Prefixlen: %u\n", info->sel.prefixlen);
        printf("    Prefix: ");
        for (int i = 0; i < info->sel.prefixlen / 8 + 1; i++) {
            printf("%02x", info->sel.prefix[i]);
        }
        printf("\n");
        printf("  Lft:\n");
        printf("    Soft Byte Limit: %llu\n", info->lft.soft_byte_limit);
        printf("    Hard Byte Limit: %llu\n", info->lft.hard_byte_limit);
        printf("    Soft Packet Limit: %llu\n", info->lft.soft_packet_limit);
        printf("    Hard Packet Limit: %llu\n", info->lft.hard_packet_limit);
        printf("    Soft Addtime: %u\n", info->lft.soft_addtime);
        printf("    Hard Addtime: %u\n", info->lft.hard_addtime);
        printf("    Soft Usecount: %u\n", info->lft.soft_use_count);
        printf("    Hard Usecount: %u\n", info->lft.hard_use_count);
        printf("    Expire: %u\n", info->lft.expire);

        // handle XFRM_MSG_GETSA in the same way as XFRM_MSG_GETPOLICY
    }

    close(sock_fd);
    return 0;
}
``
用户层通过XFRM_MSG_GETSA获取全部SA的C代码

原文地址: https://www.cveoy.top/t/topic/fWPi 著作权归作者所有。请勿转载和采集!

免费AI点我,无需注册和登录