1 /*- 2 * SPDX-License-Identifier: BSD-2-Clause-FreeBSD 3 * 4 * Copyright (c) 2012 The FreeBSD Foundation 5 * 6 * This software was developed by Edward Tomasz Napierala under sponsorship 7 * from the FreeBSD Foundation. 8 * 9 * Redistribution and use in source and binary forms, with or without 10 * modification, are permitted provided that the following conditions 11 * are met: 12 * 1. Redistributions of source code must retain the above copyright 13 * notice, this list of conditions and the following disclaimer. 14 * 2. Redistributions in binary form must reproduce the above copyright 15 * notice, this list of conditions and the following disclaimer in the 16 * documentation and/or other materials provided with the distribution. 17 * 18 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 19 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 20 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 21 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 22 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 23 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 24 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 25 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 26 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 27 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 28 * SUCH DAMAGE. 29 */ 30 31 #ifndef __LIBISCSIUTIL_H__ 32 #define __LIBISCSIUTIL_H__ 33 34 #include <sys/types.h> 35 #include <stdbool.h> 36 37 struct connection_ops; 38 39 #define CONN_DIGEST_NONE 0 40 #define CONN_DIGEST_CRC32C 1 41 42 struct connection { 43 const struct connection_ops *conn_ops; 44 int conn_socket; 45 uint8_t conn_isid[6]; 46 uint16_t conn_tsih; 47 uint32_t conn_cmdsn; 48 uint32_t conn_statsn; 49 int conn_header_digest; 50 int conn_data_digest; 51 bool conn_immediate_data; 52 bool conn_use_proxy; 53 int conn_max_recv_data_segment_length; 54 int conn_max_send_data_segment_length; 55 int conn_max_burst_length; 56 int conn_first_burst_length; 57 int conn_ping_timeout; 58 int conn_login_timeout; 59 }; 60 61 struct pdu { 62 struct connection *pdu_connection; 63 struct iscsi_bhs *pdu_bhs; 64 char *pdu_data; 65 size_t pdu_data_len; 66 }; 67 68 struct connection_ops { 69 bool (*timed_out)(void); 70 void (*pdu_receive_proxy)(struct pdu *); 71 void (*pdu_send_proxy)(struct pdu *); 72 void (*fail)(const struct connection *, const char *); 73 }; 74 75 #define KEYS_MAX 1024 76 77 struct keys { 78 char *keys_names[KEYS_MAX]; 79 char *keys_values[KEYS_MAX]; 80 }; 81 82 #define CHAP_CHALLENGE_LEN 1024 83 #define CHAP_DIGEST_LEN 16 /* Equal to MD5 digest size. */ 84 85 struct chap { 86 unsigned char chap_id; 87 char chap_challenge[CHAP_CHALLENGE_LEN]; 88 char chap_response[CHAP_DIGEST_LEN]; 89 }; 90 91 struct rchap { 92 char *rchap_secret; 93 unsigned char rchap_id; 94 void *rchap_challenge; 95 size_t rchap_challenge_len; 96 }; 97 98 struct chap *chap_new(void); 99 char *chap_get_id(const struct chap *chap); 100 char *chap_get_challenge(const struct chap *chap); 101 int chap_receive(struct chap *chap, const char *response); 102 int chap_authenticate(struct chap *chap, 103 const char *secret); 104 void chap_delete(struct chap *chap); 105 106 struct rchap *rchap_new(const char *secret); 107 int rchap_receive(struct rchap *rchap, 108 const char *id, const char *challenge); 109 char *rchap_get_response(struct rchap *rchap); 110 void rchap_delete(struct rchap *rchap); 111 112 struct keys *keys_new(void); 113 void keys_delete(struct keys *key); 114 void keys_load(struct keys *keys, const char *data, 115 size_t len); 116 void keys_save(struct keys *keys, char **datap, 117 size_t *lenp); 118 const char *keys_find(struct keys *keys, const char *name); 119 void keys_add(struct keys *keys, 120 const char *name, const char *value); 121 void keys_add_int(struct keys *keys, 122 const char *name, int value); 123 124 static __inline void 125 keys_load_pdu(struct keys *keys, const struct pdu *pdu) 126 { 127 keys_load(keys, pdu->pdu_data, pdu->pdu_data_len); 128 } 129 130 static __inline void 131 keys_save_pdu(struct keys *keys, struct pdu *pdu) 132 { 133 keys_save(keys, &pdu->pdu_data, &pdu->pdu_data_len); 134 } 135 136 struct pdu *pdu_new(struct connection *ic); 137 struct pdu *pdu_new_response(struct pdu *request); 138 int pdu_ahs_length(const struct pdu *pdu); 139 int pdu_data_segment_length(const struct pdu *pdu); 140 void pdu_set_data_segment_length(struct pdu *pdu, 141 uint32_t len); 142 void pdu_receive(struct pdu *request); 143 void pdu_send(struct pdu *response); 144 void pdu_delete(struct pdu *ip); 145 146 void text_send_request(struct connection *conn, 147 struct keys *request_keys); 148 struct keys * text_read_response(struct connection *conn); 149 struct keys * text_read_request(struct connection *conn, 150 struct pdu **requestp); 151 void text_send_response(struct pdu *request, 152 struct keys *response_keys); 153 154 void connection_init(struct connection *conn, 155 const struct connection_ops *ops, bool use_proxy); 156 157 void log_init(int level); 158 void log_set_peer_name(const char *name); 159 void log_set_peer_addr(const char *addr); 160 void log_err(int, const char *, ...) 161 __dead2 __printflike(2, 3); 162 void log_errx(int, const char *, ...) 163 __dead2 __printflike(2, 3); 164 void log_warn(const char *, ...) __printflike(1, 2); 165 void log_warnx(const char *, ...) __printflike(1, 2); 166 void log_debugx(const char *, ...) __printflike(1, 2); 167 168 char *checked_strdup(const char *); 169 170 #endif /* !__LIBISCSIUTIL_H__ */ 171