// SPDX-License-Identifier: GPL-2.0 OR BSD-3-Clause
#ifndef __YNL_C_H
#define __YNL_C_H 1
#include <stdbool.h>
#include <stddef.h>
#include <linux/genetlink.h>
#include <linux/types.h>
#include "ynl-priv.h"
enum ynl_error_code {
YNL_ERROR_NONE = 0 ,
__YNL_ERRNO_END = 4096 ,
YNL_ERROR_INTERNAL,
YNL_ERROR_DUMP_INTER,
YNL_ERROR_EXPECT_ACK,
YNL_ERROR_EXPECT_MSG,
YNL_ERROR_UNEXPECT_MSG,
YNL_ERROR_ATTR_MISSING,
YNL_ERROR_ATTR_INVALID,
YNL_ERROR_UNKNOWN_NTF,
YNL_ERROR_INV_RESP,
YNL_ERROR_INPUT_INVALID,
YNL_ERROR_INPUT_TOO_BIG,
YNL_ERROR_SUBMSG_KEY,
};
/**
* struct ynl_error - error encountered by YNL
* @ code : errno ( low values ) or YNL error code ( enum ynl_error_code )
* @ attr_offs : offset of bad attribute ( for very advanced users )
* @ msg : error message
*
* Error information for when YNL operations fail .
* Users should interact with the err member of struct ynl_sock directly .
* The main exception to that rule is ynl_sock_create ( ) .
*/
struct ynl_error {
enum ynl_error_code code;
unsigned int attr_offs;
char msg[512 ];
};
/**
* struct ynl_family - YNL family info
* Family description generated by codegen . Pass to ynl_sock_create ( ) .
*/
struct ynl_family {
/* private: */
const char *name;
size_t hdr_len;
bool is_classic;
__u16 classic_id;
const struct ynl_ntf_info *ntf_info;
unsigned int ntf_info_size;
};
/**
* struct ynl_sock - YNL wrapped netlink socket
* @ err : YNL error descriptor , cleared on every request .
*/
struct ynl_sock {
struct ynl_error err;
/* private: */
const struct ynl_family *family;
int socket;
__u32 seq;
__u32 portid;
__u16 family_id;
unsigned int n_mcast_groups;
struct {
unsigned int id;
char name[GENL_NAMSIZ];
} *mcast_groups;
struct ynl_ntf_base_type *ntf_first;
struct ynl_ntf_base_type **ntf_last_next;
struct nlmsghdr *nlh;
const struct ynl_policy_nest *req_policy;
size_t req_hdr_len;
unsigned char *tx_buf;
unsigned char *rx_buf;
unsigned char raw_buf[];
};
/**
* struct ynl_string - parsed individual string
* @ len : length of the string ( excluding terminating character )
* @ str : value of the string
*
* Parsed and nul - terminated string . This struct is only used for arrays of
* strings . Non - array string members are placed directly in respective types .
*/
struct ynl_string {
unsigned int len;
char str[];
};
struct ynl_sock *
ynl_sock_create(const struct ynl_family *yf, struct ynl_error *e);
void ynl_sock_destroy(struct ynl_sock *ys);
#define ynl_dump_foreach(dump, iter) \
for (typeof(dump->obj) *iter = &dump->obj; \
!ynl_dump_obj_is_last(iter); \
iter = ynl_dump_obj_next(iter))
/**
* ynl_dump_empty ( ) - does the dump have no entries
* @ dump : pointer to the dump list , as returned by a dump call
*
* Check if the dump is empty , i . e . contains no objects .
* Dump calls return NULL on error , and terminator element if empty .
*/
static inline bool ynl_dump_empty(void *dump)
{
return dump == (void *)YNL_LIST_END;
}
int ynl_subscribe(struct ynl_sock *ys, const char *grp_name);
int ynl_socket_get_fd(struct ynl_sock *ys);
int ynl_ntf_check(struct ynl_sock *ys);
/**
* ynl_has_ntf ( ) - check if socket has * parsed * notifications
* @ ys : active YNL socket
*
* Note that this does not take into account notifications sitting
* in netlink socket , just the notifications which have already been
* read and parsed ( e . g . during a ynl_ntf_check ( ) call ) .
*/
static inline bool ynl_has_ntf(struct ynl_sock *ys)
{
return ys->ntf_last_next != &ys->ntf_first;
}
struct ynl_ntf_base_type *ynl_ntf_dequeue(struct ynl_sock *ys);
void ynl_ntf_free(struct ynl_ntf_base_type *ntf);
#endif
Messung V0.5 in Prozent C=96 H=91 G=93
¤ Dauer der Verarbeitung: 0.5 Sekunden
¤
*© Formatika GbR, Deutschland