]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sbin/iscontrol/misc.c
Optionally bind ktls threads to NUMA domains
[FreeBSD/FreeBSD.git] / sbin / iscontrol / misc.c
1 /*-
2  * SPDX-License-Identifier: BSD-2-Clause-FreeBSD
3  *
4  * Copyright (c) 2005-2010 Daniel Braniss <danny@cs.huji.ac.il>
5  * All rights reserved.
6  *
7  * Redistribution and use in source and binary forms, with or without
8  * modification, are permitted provided that the following conditions
9  * are met:
10  * 1. Redistributions of source code must retain the above copyright
11  *    notice, this list of conditions and the following disclaimer.
12  * 2. Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
17  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
20  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26  * SUCH DAMAGE.
27  *
28  */
29
30 /*
31  | $Id: misc.c,v 2.1 2006/11/12 08:06:51 danny Exp $
32  */
33
34 #include <sys/cdefs.h>
35 __FBSDID("$FreeBSD$");
36
37 #include <sys/param.h>
38 #include <sys/types.h>
39 #include <sys/socket.h>
40 #include <sys/sysctl.h>
41
42 #include <netinet/in.h>
43 #include <netinet/tcp.h>
44 #include <arpa/inet.h>
45 #include <stdlib.h>
46 #include <stdio.h>
47 #include <string.h>
48
49 #include <dev/iscsi_initiator/iscsi.h>
50 #include "iscontrol.h"
51
52 static inline char
53 c2b(unsigned char c)
54 {
55      switch(c) {
56      case '0' ... '9':
57           return c - '0';
58      case 'a' ... 'f':
59           return c - 'a' + 10;
60      case 'A' ... 'F':
61           return c - 'A' + 10;
62      }
63      return 0;
64 }
65
66 static char     base64[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
67                            "abcdefghijklmnopqrstuvwxyz"
68                            "0123456789+/";
69
70 static __inline unsigned char
71 c64tobin(unsigned char c64)
72 {
73      int        i;
74      for(i = 0; i < 64; i++)
75           if(base64[i] == c64)
76                break;
77      return i;
78 }
79 /*
80  | according to rfc3720, the binary string
81  | cannot be larger than 1024 - but i can't find it :-) XXX
82  | not enforced yet.
83  */
84 int
85 str2bin(char *str, char **rsp)
86 {
87      char       *src, *dst, *tmp;
88      int        i, len = 0;
89
90      src = str;
91      tmp = NULL;
92      if(strncasecmp("0x", src, 2) == 0) {
93           src += 2;
94           len = strlen(src);
95           
96           if((tmp = malloc((len+1)/2)) == NULL) {
97                // XXX: print some error?
98                return 0;
99           }
100           dst = tmp;
101           if(len & 1)
102                *dst++ = c2b(*src++);
103           while(*src) {
104                *dst = c2b(*src++) << 4;
105                *dst++ |= c2b(*src++);
106           }
107           len = dst - tmp;
108      } else
109      if(strncasecmp("0b", src , 2) == 0) {
110           // base64
111           unsigned char b6;
112
113           src += 2;
114           len = strlen(src) / 4 * 3;
115           if((tmp = malloc(len)) == NULL) {
116                // XXX: print some error?
117                return 0;
118           }
119           dst = tmp; 
120           i = 0;
121           while(*src && ((b6 = c64tobin(*src++)) != 64)) {
122                switch(i % 4) {
123                case 0:
124                     *dst = b6 << 2;
125                     break;
126                case 1:
127                     *dst++ |= b6 >> 4;
128                     *dst = b6 << 4;
129                     break;
130                case 2:
131                     *dst++ |= b6 >> 2;
132                     *dst = b6 << 6;
133                     break;
134                case 3:
135                     *dst++ |= b6;
136                     break;
137                }
138                i++;
139           }
140           len = dst - tmp;
141      }
142      else {
143           /*
144            | assume it to be an ascii string, so just copy it
145            */
146           len = strlen(str);
147           if((tmp = malloc(len)) == NULL)
148                return 0;
149           dst = tmp;
150           src = str;
151           while(*src)
152                *dst++ = *src++;
153      }
154
155      *rsp = tmp;
156      return len;
157 }
158
159 char *
160 bin2str(char *encoding, unsigned char *md, int blen)
161 {
162      int        len;
163      char       *dst, *ds;
164      unsigned char *cp;
165
166      if(strncasecmp(encoding, "0x", 2) == 0) {
167           char  ofmt[5];
168
169           len = blen * 2;
170           dst = malloc(len + 3);
171           strcpy(dst, encoding);
172           ds = dst + 2;
173           cp = md;
174           sprintf(ofmt, "%%02%c", encoding[1]);
175           while(blen-- > 0) {
176                sprintf(ds, ofmt, *cp++);
177                ds += 2;
178           }
179           *ds = 0;
180           return dst;
181      }
182      if(strncasecmp(encoding, "0b", 2) == 0) {
183           int i, b6;
184
185           len = (blen + 2) * 4 / 3;
186           dst = malloc(len + 3);
187           strcpy(dst, encoding);
188           ds = dst + 2;
189           cp = md;
190           b6 = 0; // to keep compiler happy.
191           for(i = 0; i < blen; i++) {
192                switch(i % 3) {
193                case 0:
194                     *ds++ = base64[*cp >> 2];
195                     b6 = (*cp & 0x3) << 4;
196                     break;
197                case 1:
198                     b6 += (*cp >> 4);
199                     *ds++ = base64[b6];
200                     b6 = (*cp & 0xf) << 2;
201                     break;
202                case 2:
203                     b6 += (*cp >> 6);
204                     *ds++ = base64[b6];
205                     *ds++ = base64[*cp & 0x3f];
206                }
207                cp++;
208           }
209           switch(blen % 3) {
210           case 0:
211                break;
212           case 1:
213                *ds++ = base64[b6];
214                *ds++ = '=';
215                *ds++ = '=';
216                break;
217           case 2:
218                *ds++ = base64[b6];
219                *ds++ = '=';
220                break;
221           }
222
223           *ds = 0;
224           return dst;
225      }
226
227      return NULL;
228 }