void send_init(struct nbr *nbr) { struct ibuf *buf; u_int16_t size; log_debug("send_init: neighbor ID %s", inet_ntoa(nbr->id)); if ((buf = ibuf_open(LDP_MAX_LEN)) == NULL) fatal("send_init"); size = LDP_HDR_SIZE + sizeof(struct ldp_msg) + SESS_PRMS_SIZE; gen_ldp_hdr(buf, size); size -= LDP_HDR_SIZE; gen_msg_tlv(buf, MSG_TYPE_INIT, size); size -= sizeof(struct ldp_msg); gen_init_prms_tlv(buf, nbr, size); evbuf_enqueue(&nbr->tcp->wbuf, buf); }
static const response* init(void) { const char* path; str rule = {0,0,0}; ibuf in; const response* r; if ((path = getenv("MAILRULES")) == 0) return 0; loaded = 1; if (!ibuf_open(&in, path, 0)) return &resp_erropen; while (ibuf_getstr(&in, &rule, LF)) { str_strip(&rule); if (rule.len == 0) continue; if (rule.s[0] == ':') { switch (rule.s[1]) { case 's': current_rules = &sender_rules; break; case 'r': current_rules = &recip_rules; break; default: return &resp_syntax; } } else if ((r = add(rule.s)) != 0) return r; } ibuf_close(&in); str_free(&rule); return 0; }
void send_address_withdraw(struct nbr *nbr, struct iface *iface) { struct ibuf *buf; u_int16_t size; if (nbr->iface->passive) return; log_debug("send_address_withdraw: neighbor ID %s", inet_ntoa(nbr->id)); if ((buf = ibuf_open(LDP_MAX_LEN)) == NULL) fatal("send_address_withdraw"); /* XXX: multiple address on the same iface? */ size = LDP_HDR_SIZE + sizeof(struct ldp_msg) + sizeof(struct in_addr); gen_ldp_hdr(buf, nbr->iface, size); size -= LDP_HDR_SIZE; gen_msg_tlv(buf, MSG_TYPE_ADDRWITHDRAW, size); size -= sizeof(struct ldp_msg); gen_address_list_tlv(buf, iface, size); evbuf_enqueue(&nbr->wbuf, buf); }
int vmailmgr_autoconvert(void) { int writefd = -1; ibuf reader; struct cdb_make writer; int error = 0; int readall = 0; int writerr = 0; if ((writefd = path_mktemp(pwfile, &tmppwfile)) != -1) { if (cdb_make_start(&writer, writefd) != 0) error = CVME_IO | CVME_FATAL; else { if (ibuf_open(&reader, pwfile, 0)) { uint32 end; struct stat st; if (fstat(reader.io.fd, &st) == 0 && fchmod(writefd, st.st_mode) == 0 && fchown(writefd, st.st_uid, st.st_gid) == 0 && read_start(&reader, &end)) { while (ibuf_tell(&reader) < end) { if (!read_cdb_pair(&reader, &key, &data)) break; if (str_diff(&key, &virtuser) == 0) if (!convert_data()) { writerr = 1; break; } if (cdb_make_add(&writer, key.s, key.len, data.s, data.len) != 0) { writerr = 1; break; } } readall = ibuf_tell(&reader) == end; } ibuf_close(&reader); } if (cdb_make_finish(&writer) != 0) error |= CVME_FATAL; else if (readall && !writerr) rename(tmppwfile.s, pwfile); } close(writefd); unlink(tmppwfile.s); } return error; }
static void dump_msg(long num, long bodylines) { ibuf in; static char buf[4096]; int in_header; /* True until a blank line is seen */ int sol; /* True if at start of line */ if (!ibuf_open(&in, msgs[num-1].filename, 0)) return respond("-ERR Could not open that message"); respond(ok); sol = in_header = 1; while (ibuf_read(&in, buf, sizeof buf) || in.count) { const char* ptr = buf; const char* end = buf + in.count; while (ptr < end) { const char* lfptr; if (sol) { if (!in_header) if (--bodylines < 0) break; if (*ptr == '.') obuf_putc(&outbuf, '.'); } if ((lfptr = memchr(ptr, LF, end-ptr)) == 0) { obuf_write(&outbuf, ptr, end-ptr); ptr = end; sol = 0; } else { if (in_header && lfptr == ptr) in_header = 0; obuf_write(&outbuf, ptr, lfptr-ptr); obuf_puts(&outbuf, CRLF); ptr = lfptr + 1; sol = 1; } } } ibuf_close(&in); obuf_puts(&outbuf, CRLF); respond("."); }
int dict_load_list(dict* d, const char* filename, int mustexist, int (*xform)(str*)) { ibuf in; str tmp = {0,0,0}; int result = 1; if (!dict_init(d)) return 0; if (!ibuf_open(&in, filename, 0)) return !mustexist; while (ibuf_getstr(&in, &tmp, '\n')) { str_strip(&tmp); if (tmp.len > 0 && tmp.s[0] != '#') { if (xform != 0) if (!xform(&tmp)) { result = 0; break; } if (!dict_add(d, &tmp, 0)) { result = 0; break; } } } str_free(&tmp); ibuf_close(&in); return result; }
void send_notification_full(struct tcp_conn *tcp, struct notify_msg *nm) { struct ibuf *buf; uint16_t size; int err = 0; /* calculate size */ size = LDP_HDR_SIZE + LDP_MSG_SIZE + STATUS_SIZE; if (nm->flags & F_NOTIF_PW_STATUS) size += PW_STATUS_TLV_SIZE; if (nm->flags & F_NOTIF_FEC) { size += TLV_HDR_SIZE; switch (nm->fec.type) { case MAP_TYPE_PWID: size += FEC_PWID_ELM_MIN_LEN; if (nm->fec.flags & F_MAP_PW_ID) size += sizeof(uint32_t); break; } } if ((buf = ibuf_open(size)) == NULL) fatal(__func__); err |= gen_ldp_hdr(buf, size); size -= LDP_HDR_SIZE; err |= gen_msg_hdr(buf, MSG_TYPE_NOTIFICATION, size); err |= gen_status_tlv(buf, nm->status_code, nm->msg_id, nm->msg_type); /* optional tlvs */ if (nm->flags & F_NOTIF_PW_STATUS) err |= gen_pw_status_tlv(buf, nm->pw_status); if (nm->flags & F_NOTIF_FEC) err |= gen_fec_tlv(buf, &nm->fec); if (err) { ibuf_free(buf); return; } evbuf_enqueue(&tcp->wbuf, buf); }
void send_keepalive(struct nbr *nbr) { struct ibuf *buf; u_int16_t size; if (nbr->iface->passive) return; if ((buf = ibuf_open(LDP_MAX_LEN)) == NULL) fatal("send_keepalive"); size = LDP_HDR_SIZE + sizeof(struct ldp_msg); gen_ldp_hdr(buf, nbr->iface, size); size -= LDP_HDR_SIZE; gen_msg_tlv(buf, MSG_TYPE_KEEPALIVE, size); evbuf_enqueue(&nbr->wbuf, buf); }
void send_address(struct nbr *nbr, struct iface *iface) { struct ibuf *buf; struct iface *niface; u_int16_t size, iface_count = 0; if (nbr->iface->passive) return; log_debug("send_address: neighbor ID %s", inet_ntoa(nbr->id)); if ((buf = ibuf_open(LDP_MAX_LEN)) == NULL) fatal("send_address"); /* XXX: multiple address on the same iface? */ if (iface == NULL) LIST_FOREACH(niface, &leconf->iface_list, entry) iface_count++; else iface_count = 1; size = LDP_HDR_SIZE + sizeof(struct ldp_msg) + sizeof(struct address_list_tlv) + iface_count * sizeof(struct in_addr); gen_ldp_hdr(buf, nbr->iface, size); size -= LDP_HDR_SIZE; gen_msg_tlv(buf, MSG_TYPE_ADDR, size); size -= sizeof(struct ldp_msg); gen_address_list_tlv(buf, iface, size); evbuf_enqueue(&nbr->wbuf, buf); }
/* DVMRP neighbors2 packet handling */ int send_nbrs2(struct iface *iface, struct in_addr addr, void *data, int len) { struct sockaddr_in dst; struct ibuf *buf; struct dvmrp_hdr *dvmrp_hdr; int ret = 0; log_debug("send_nbrs2: interface %s addr %s", iface->name, inet_ntoa(addr)); if (iface->passive) return (0); if ((buf = ibuf_open(iface->mtu - sizeof(struct ip))) == NULL) fatal("send_nbrs2"); /* DVMRP header */ if (gen_dvmrp_hdr(buf, iface, DVMRP_CODE_GRAFT_ACK)) goto fail; dst.sin_family = AF_INET; dst.sin_len = sizeof(struct sockaddr_in); dst.sin_addr.s_addr = addr.s_addr; /* update chksum */ dvmrp_hdr = ibuf_seek(buf, 0, sizeof(dvmrp_hdr)); dvmrp_hdr->chksum = in_cksum(buf->buf, buf->wpos); ret = send_packet(iface, buf->buf, buf->wpos, &dst); ibuf_free(buf); return (ret); fail: log_warn("send_nbrs2"); ibuf_free(buf); return (-1); }
int send_hello(struct iface *iface) { struct sockaddr_in dst; struct ibuf *buf; u_int16_t size; dst.sin_port = htons(LDP_PORT); dst.sin_family = AF_INET; dst.sin_len = sizeof(struct sockaddr_in); inet_aton(AllRouters, &dst.sin_addr); if (iface->passive) return (0); if ((buf = ibuf_open(LDP_MAX_LEN)) == NULL) fatal("send_hello"); size = LDP_HDR_SIZE + sizeof(struct ldp_msg) + sizeof(struct hello_prms_tlv); gen_ldp_hdr(buf, iface, size); size -= LDP_HDR_SIZE; gen_msg_tlv(buf, MSG_TYPE_HELLO, size); size -= sizeof(struct ldp_msg); gen_hello_prms_tlv(iface, buf, size); send_packet(iface, buf->buf, buf->wpos, &dst); ibuf_free(buf); return (0); }
struct ibuf * send_notification(u_int32_t status, struct iface *iface, u_int32_t msgid, u_int32_t type) { struct ibuf *buf; u_int16_t size; if ((buf = ibuf_open(LDP_MAX_LEN)) == NULL) fatal("send_notification"); size = LDP_HDR_SIZE + sizeof(struct ldp_msg) + STATUS_SIZE; gen_ldp_hdr(buf, iface, size); size -= LDP_HDR_SIZE; gen_msg_tlv(buf, MSG_TYPE_NOTIFICATION, size); size -= sizeof(struct ldp_msg); gen_status_tlv(buf, status, msgid, type); return (buf); }
/* database description packet handling */ int send_db_description(struct nbr *nbr) { struct in6_addr dst; struct db_dscrp_hdr dd_hdr; struct lsa_entry *le, *nle; struct ibuf *buf; int ret = 0; u_int8_t bits = 0; if ((buf = ibuf_open(nbr->iface->mtu - sizeof(struct ip))) == NULL) fatal("send_db_description"); /* OSPF header */ if (gen_ospf_hdr(buf, nbr->iface, PACKET_TYPE_DD)) goto fail; /* reserve space for database description header */ if (ibuf_reserve(buf, sizeof(dd_hdr)) == NULL) goto fail; switch (nbr->state) { case NBR_STA_DOWN: case NBR_STA_ATTEMPT: case NBR_STA_INIT: case NBR_STA_2_WAY: case NBR_STA_SNAP: log_debug("send_db_description: cannot send packet in state %s," " neighbor ID %s", nbr_state_name(nbr->state), inet_ntoa(nbr->id)); ret = -1; goto done; case NBR_STA_XSTRT: bits |= OSPF_DBD_MS | OSPF_DBD_M | OSPF_DBD_I; nbr->dd_more = 1; break; case NBR_STA_XCHNG: if (nbr->dd_master) bits |= OSPF_DBD_MS; else bits &= ~OSPF_DBD_MS; if (TAILQ_EMPTY(&nbr->db_sum_list)) { bits &= ~OSPF_DBD_M; nbr->dd_more = 0; } else { bits |= OSPF_DBD_M; nbr->dd_more = 1; } bits &= ~OSPF_DBD_I; /* build LSA list */ for (le = TAILQ_FIRST(&nbr->db_sum_list); le != NULL && buf->wpos + sizeof(struct lsa_hdr) < buf->max; le = nle) { nbr->dd_end = nle = TAILQ_NEXT(le, entry); if (ibuf_add(buf, le->le_lsa, sizeof(struct lsa_hdr))) goto fail; } break; case NBR_STA_LOAD: case NBR_STA_FULL: if (nbr->dd_master) bits |= OSPF_DBD_MS; else bits &= ~OSPF_DBD_MS; bits &= ~OSPF_DBD_M; bits &= ~OSPF_DBD_I; nbr->dd_more = 0; break; default: fatalx("send_db_description: unknown neighbor state"); } bzero(&dd_hdr, sizeof(dd_hdr)); switch (nbr->iface->type) { case IF_TYPE_POINTOPOINT: inet_pton(AF_INET6, AllSPFRouters, &dst); dd_hdr.iface_mtu = htons(nbr->iface->mtu); break; case IF_TYPE_BROADCAST: dst = nbr->addr; dd_hdr.iface_mtu = htons(nbr->iface->mtu); break; case IF_TYPE_NBMA: case IF_TYPE_POINTOMULTIPOINT: /* XXX not supported */ break; case IF_TYPE_VIRTUALLINK: dst = nbr->iface->dst; dd_hdr.iface_mtu = 0; break; default: fatalx("send_db_description: unknown interface type"); } dd_hdr.opts = htonl(area_ospf_options(area_find(oeconf, nbr->iface->area_id))); dd_hdr.bits = bits; dd_hdr.dd_seq_num = htonl(nbr->dd_seq_num); memcpy(ibuf_seek(buf, sizeof(struct ospf_hdr), sizeof(dd_hdr)), &dd_hdr, sizeof(dd_hdr)); /* calculate checksum */ if (upd_ospf_hdr(buf, nbr->iface)) goto fail; /* transmit packet */ ret = send_packet(nbr->iface, buf->buf, buf->wpos, &dst); done: ibuf_free(buf); return (ret); fail: log_warn("send_db_description"); ibuf_free(buf); return (-1); }