n-acd.h 3.55 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
#pragma once

/*
 * IPv4 Address Conflict Detection
 *
 * This is the public header of the n-acd library, implementing IPv4 Address
 * Conflict Detection as described in RFC-5227. This header defines the public
 * API and all entry points of n-acd.
 */

#ifdef __cplusplus
extern "C" {
#endif

#include <netinet/in.h>
16
#include <inttypes.h>
17
#include <stdbool.h>
18
#include <stdlib.h>
19

20 21 22 23 24 25 26 27
typedef struct NAcd NAcd;
typedef struct NAcdConfig NAcdConfig;
typedef struct NAcdEvent NAcdEvent;
typedef struct NAcdProbe NAcdProbe;
typedef struct NAcdProbeConfig NAcdProbeConfig;

#define N_ACD_TIMEOUT_RFC5227 (UINT64_C(9000))

28 29 30 31 32 33
enum {
        _N_ACD_E_SUCCESS,

        N_ACD_E_PREEMPTED,
        N_ACD_E_INVALID_ARGUMENT,

34 35
        _N_ACD_E_N,
};
36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57

enum {
        N_ACD_TRANSPORT_ETHERNET,
        _N_ACD_TRANSPORT_N,
};

enum {
        N_ACD_EVENT_READY,
        N_ACD_EVENT_USED,
        N_ACD_EVENT_DEFENDED,
        N_ACD_EVENT_CONFLICT,
        N_ACD_EVENT_DOWN,
        _N_ACD_EVENT_N,
};

enum {
        N_ACD_DEFEND_NEVER,
        N_ACD_DEFEND_ONCE,
        N_ACD_DEFEND_ALWAYS,
        _N_ACD_DEFEND_N,
};

58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74
struct NAcdEvent {
        unsigned int event;
        union {
                struct {
                        NAcdProbe *probe;
                } ready;
                struct {
                } down;
                struct {
                        NAcdProbe *probe;
                        uint8_t *sender;
                        size_t n_sender;
                } used, defended, conflict;
        };
};

/* configs */
75

76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93
int n_acd_config_new(NAcdConfig **configp);
NAcdConfig *n_acd_config_free(NAcdConfig *config);

void n_acd_config_set_ifindex(NAcdConfig *config, int ifindex);
void n_acd_config_set_transport(NAcdConfig *config, unsigned int transport);
void n_acd_config_set_mac(NAcdConfig *config, const uint8_t *mac, size_t n_mac);

int n_acd_probe_config_new(NAcdProbeConfig **configp);
NAcdProbeConfig *n_acd_probe_config_free(NAcdProbeConfig *config);

void n_acd_probe_config_set_ip(NAcdProbeConfig *config, struct in_addr ip);
void n_acd_probe_config_set_timeout(NAcdProbeConfig *config, uint64_t msecs);

/* contexts */

int n_acd_new(NAcd **acdp, NAcdConfig *config);
NAcd *n_acd_ref(NAcd *acd);
NAcd *n_acd_unref(NAcd *acd);
94

95
void n_acd_get_fd(NAcd *acd, int *fdp);
96 97 98
int n_acd_dispatch(NAcd *acd);
int n_acd_pop_event(NAcd *acd, NAcdEvent **eventp);

99 100 101 102 103 104 105 106
int n_acd_probe(NAcd *acd, NAcdProbe **probep, NAcdProbeConfig *config);

/* probes */

NAcdProbe *n_acd_probe_free(NAcdProbe *probe);

void n_acd_probe_set_userdata(NAcdProbe *probe, void *userdata);
void n_acd_probe_get_userdata(NAcdProbe *probe, void **userdatap);
107

108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130
int n_acd_probe_announce(NAcdProbe *probe, unsigned int defend);

/* inline helpers */

static inline void n_acd_config_freep(NAcdConfig **config) {
        if (*config)
                n_acd_config_free(*config);
}

static inline void n_acd_config_freev(NAcdConfig *config) {
        n_acd_config_free(config);
}

static inline void n_acd_probe_config_freep(NAcdProbeConfig **config) {
        if (*config)
                n_acd_probe_config_free(*config);
}

static inline void n_acd_probe_config_freev(NAcdProbeConfig *config) {
        n_acd_probe_config_free(config);
}

static inline void n_acd_unrefp(NAcd **acd) {
131
        if (*acd)
132 133 134 135 136 137 138 139 140 141 142 143 144 145
                n_acd_unref(*acd);
}

static inline void n_acd_unrefv(NAcd *acd) {
        n_acd_unref(acd);
}

static inline void n_acd_probe_freep(NAcdProbe **probe) {
        if (*probe)
                n_acd_probe_free(*probe);
}

static inline void n_acd_probe_freev(NAcdProbe *probe) {
        n_acd_probe_free(probe);
146 147 148 149 150
}

#ifdef __cplusplus
}
#endif