1 /*
2 Copyright (C) 2017-2021, Dirk Krause
3 SPDX-License-Identifier: BSD-3-Clause
4 */
5 
6 /*
7 	WARNING: This file was generated by the dkct program (see
8 	http://dktools.sourceforge.net/ for details).
9 	Changes you make here will be lost if dkct is run again!
10 	You should modify the original source and run dkct on it.
11 	Original source: dk4sock04.ctr
12 */
13 
14 /**	@file dk4sock04.c The dk4sock04 module.
15 */
16 
17 
18 #include "dk4conf.h"
19 #include <libdk4sock/dk4sock.h>
20 #include <libdk4base/dk4mem.h>
21 #include <libdk4base/dk4strw.h>
22 #include <libdk4base/dk4strd.h>
23 #include <libdk4maiowd/dk4maowd.h>
24 #include <libdk4maiowh/dk4maowh.h>
25 #include <libdk4c/dk4rec23.h>
26 
27 #include <libdk4base/dk4unused.h>
28 
29 #if DK4_HAVE_ASSERT_H
30 #ifndef	ASSERT_H_INCLUDED
31 #include <assert.h>
32 #define	ASSERT_H_INCLUDED 1
33 #endif
34 #endif
35 
36 
37 
38 
39 
40 #if DK4_ON_WINDOWS
41 /**     Constant texts used by the module, not localized.
42 */
43 static const wchar_t * const       dk4socket_wc_kw[] = {
44 /* 0 */
45 L"@",
46 
47 /* 1 */
48 L".",
49 
50 /* 2 */
51 L":",
52 
53 NULL
54 
55 };
56 #endif
57 
58 
59 
60 int
dk4socket_wc_inet_ntop(wchar_t * dptr,size_t dsz,int afam,const void * src,dk4_er_t * erp)61 dk4socket_wc_inet_ntop(
62 #if DK4_ON_WINDOWS
63   wchar_t		*dptr,
64   size_t		 dsz,
65   int			 afam,
66   const void		*src,
67 #else
68   wchar_t		* DK4_ARG_UNUSED(dptr),
69   size_t		 DK4_ARG_UNUSED(dsz),
70   int			 DK4_ARG_UNUSED(afam),
71   const void		* DK4_ARG_UNUSED(src),
72 #endif
73   dk4_er_t		*erp
74 )
75 {
76 #if DK4_ON_WINDOWS
77 #if DK4_HAVE_INET_NTOP
78   /* +++++ +Windows +inet_ntop */
79 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
80   struct in6_addr	 in6;
81 #endif
82   struct in_addr 	 in4;
83   int			 back	= DK4_SOCKET_RESULT_FAILED;
84 
85 #if	DK4_USE_ASSERT
86   assert(NULL != dptr);
87   assert(NULL != src);
88   assert(0 < dsz);
89 #endif
90   if ((NULL != dptr) && (0 < dsz)) { *dptr = L'\0'; }
91   if ((NULL != dptr) && (NULL != src) && (0 < dsz)) {
92     dk4socket_error_reset();
93     switch (afam) {
94       case AF_INET : {
95         DK4_MEMCPY(&in4, src, sizeof(in4));
96 	if (NULL != InetNtopW(afam, (void *)(&in4), dptr, dsz)) {
97 	  back = DK4_SOCKET_RESULT_SUCCESS;
98 	} else {
99 	  dk4socket_error_report(erp, DK4_E_SOCKET_INET_NTOP);
100 	}
101       } break;
102 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
103       case AF_INET6 : {
104         DK4_MEMCPY(&in6, src, sizeof(in6));
105 	if (NULL != InetNtopW(afam, (void *)(&in6), dptr, dsz)) {
106 	  back = DK4_SOCKET_RESULT_SUCCESS;
107 	} else {
108 	  dk4socket_error_report(erp, DK4_E_SOCKET_INET_NTOP);
109 	}
110       } break;
111 #endif
112       default : {
113         dk4error_set_simple_error_code(erp, DK4_E_INVALID_ARGUMENTS);
114       } break;
115     }
116   } else {
117     dk4error_set_simple_error_code(erp, DK4_E_INVALID_ARGUMENTS);
118   }
119   return back;
120   /* ----- +Windows +inet_ntop */
121 #else
122   /* +++++ +Windows -inet_ntop */
123   wchar_t		 buf[16*sizeof(dk4_um_t)];
124   const struct in_addr	*inp4;
125 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
126   const struct in6_addr	*inp6;
127 #endif
128   unsigned long		 ul;
129   unsigned long		 u1;
130   int			 back	=	DK4_SOCKET_RESULT_FAILED;
131 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
132   int			 i;
133 #endif
134   int			 res;
135 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
136   unsigned short	 us;
137 #endif
138 #if	DK4_USE_ASSERT
139   assert(NULL != dptr);
140   assert(NULL != src);
141   assert(0 < dsz);
142 #endif
143   if ((NULL != dptr) && (0 < dsz)) { *dptr = L'\0'; }
144   if ((NULL != dptr) && (NULL != src) && (0 < dsz)) {
145     switch (afam) {
146       case AF_INET : {
147         inp4 = (const struct in_addr *)src;
148 	ul = inp4->s_addr;
149 	ul = dk4socket_htonl(ul);
150 	u1 = ((ul >> 24) & 0x000000FFUL);
151 	res = dk4ma_write_wc_decimal_unsigned(
152 	  buf, sizeof(buf), (dk4_um_t)u1, 0, erp
153 	);
154 	if (0 != res) {
155 	  if (0 != dk4strw_cpy_s(dptr, dsz, buf, erp)) {
156 	    u1 = ((ul >> 16) & 0x000000FFUL);
157 	    res = dk4ma_write_wc_decimal_unsigned(
158 	      buf, sizeof(buf), (dk4_um_t)u1, 0, erp
159 	    );
160 	    if (0 != res) {
161 	      if (0 != dk4strw_cat_s(dptr, dsz, dk4socket_wc_kw[1], erp)) {
162 	        if (0 != dk4strw_cat_s(dptr, dsz, buf, erp)) {
163 		  u1 = ((ul >> 8) & 0x000000FFUL);
164 		  res = dk4ma_write_wc_decimal_unsigned(
165 		    buf, sizeof(buf), (dk4_um_t)u1, 0, erp
166 		  );
167 		  if (0 != res) {
168 		    if (0 != dk4strw_cat_s(dptr,dsz,dk4socket_wc_kw[1],erp)) {
169 		      if (0 != dk4strw_cat_s(dptr, dsz, buf, erp)) {
170 		        u1 = (ul & 0x000000FFUL);
171 			res = dk4ma_write_wc_decimal_unsigned(
172 			  buf, sizeof(buf), (dk4_um_t)u1, 0, erp
173 			);
174 			if (0 != res) {
175 			  if (
176 			    0 != dk4strw_cat_s(dptr,dsz,dk4socket_wc_kw[1],erp)
177 			  )
178 			  {
179 			    if (0 != dk4strw_cat_s(dptr, dsz, buf, erp)) {
180 			      back = DK4_SOCKET_RESULT_SUCCESS;
181 			    }
182 			  }
183 			}
184 		      }
185 		    }
186 		  }
187 		}
188 	      }
189 	    }
190 	  }
191 	}
192       } break;
193 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
194       case AF_INET6 : {
195         inp6 = (const struct in6_addr *)src;
196 	back = DK4_SOCKET_RESULT_SUCCESS;
197 	for (i = 0; i < 8; i++) {
198 #if DK4_ON_WINDOWS
199 	  us = inp6->u.Word[i];
200 #else
201 	  us = inp6->s6_addr16[i];
202 #endif
203 	  us = dk4socket_htons(us);
204 	  res = dk4ma_write_wc_hex_unsigned(
205 	    buf, sizeof(buf), (dk4_um_t)us, 0, erp
206 	  );
207 	  if (0 != res) {
208 	    if (0 == i) {
209 	      if (0 == dk4strw_cpy_s(dptr, dsz, buf, erp)) {
210 	        back = DK4_SOCKET_RESULT_FAILED;
211 		i = 8;
212 	      }
213 	    } else {
214 	      if (0 != dk4strw_cat_s(dptr, dsz, dk4socket_wc_kw[2], erp)) {
215 	        if (0 != dk4strw_cat_s(dptr, dsz, buf, erp)) {
216 		  back = DK4_SOCKET_RESULT_FAILED;
217 		  i = 8;
218 		}
219 	      } else {
220 	        back = DK4_SOCKET_RESULT_FAILED;
221 		i = 8;
222 	      }
223 	    }
224 	  } else {
225 	    back = DK4_SOCKET_RESULT_FAILED;
226 	    i = 8;
227 	  }
228 	}
229       } break;
230 #endif
231       default : {
232         dk4error_set_simple_error_code(erp, DK4_E_INVALID_ARGUMENTS);
233       } break;
234     }
235   } else {
236     dk4error_set_simple_error_code(erp, DK4_E_INVALID_ARGUMENTS);
237   }
238   return back;
239   /* ----- +Windows -inet_ntop */
240 #endif
241 #else
242   DK4_UNUSED_ARG(dptr)
243   DK4_UNUSED_ARG(dsz)
244   DK4_UNUSED_ARG(afam)
245   DK4_UNUSED_ARG(src)
246   dk4error_set_simple_error_code(erp, DK4_E_NOT_SUPPORTED);
247   return DK4_SOCKET_RESULT_FAILED;
248 #endif
249 }
250 
251 
252 
253 int
dk4socket_wc_addr_port_to_text(wchar_t * dptr,size_t dsz,int DK4_ARG_UNUSED (afam),const struct sockaddr * saptr,size_t sasz,dk4_er_t * erp)254 dk4socket_wc_addr_port_to_text(
255 #if DK4_ON_WINDOWS
256   wchar_t		*dptr,
257   size_t		 dsz,
258 #if DK4_HAVE_GETNAMEINFO
259   int			 DK4_ARG_UNUSED(afam),
260 #else
261   int			 afam,
262 #endif
263   const struct sockaddr	*saptr,
264   size_t		 sasz,
265 #else
266   wchar_t		* DK4_ARG_UNUSED(dptr),
267   size_t		 DK4_ARG_UNUSED(dsz),
268   int			 DK4_ARG_UNUSED(afam),
269   const struct sockaddr	* DK4_ARG_UNUSED(saptr),
270   size_t		 DK4_ARG_UNUSED(sasz),
271 #endif
272   dk4_er_t		*erp
273 )
274 {
275 #if DK4_ON_WINDOWS
276 #if DK4_HAVE_GETNAMEINFO
277   /* +++++ +getnameinfo */
278   wchar_t		 hbuf[64];
279   wchar_t		 pbuf[64];
280   const DWORD		 szh	= DK4_SIZEOF(hbuf,wchar_t);
281   const DWORD		 szp	= DK4_SIZEOF(pbuf,wchar_t);
282   int			 back	= DK4_SOCKET_RESULT_FAILED;
283   int			 res;
284   DK4_UNUSED_ARG(afam)
285 #if	DK4_USE_ASSERT
286   assert(NULL != dptr);
287   assert(NULL != saptr);
288   assert(0 < dsz);
289   assert(0 < sasz);
290 #endif
291   if ((NULL != dptr) && (0 < dsz)) { *dptr = '\0'; }
292   if ((NULL != dptr) && (NULL != saptr) && (0 < dsz) && (0 < sasz))  {
293     res = NI_NUMERICHOST | NI_NUMERICSERV;
294     dk4socket_error_reset();
295 #if DK4_HAVE_SOCKLEN_T
296     res = GetNameInfoW(saptr, (socklen_t)sasz, hbuf, szh, pbuf, szp, res);
297 #else
298     res = GetNameInfoW(saptr, sasz, hbuf, szh, pbuf, szp, res);
299 #endif
300     if (0 == res) {
301       if (0 != dk4strw_cpy_s(dptr, dsz, pbuf, erp)) {
302         if (0 != dk4strw_cat_s(dptr, dsz, dk4socket_wc_kw[0], erp)) {
303 	  if (0 != dk4strw_cat_s(dptr, dsz, hbuf, erp)) {
304 	    back = DK4_SOCKET_RESULT_SUCCESS;
305 	  }
306 	}
307       }
308     } else {
309       dk4error_set_idetails(erp, DK4_E_SOCKET_GETADDRINFO, res);
310     }
311   } else {
312     dk4error_set_simple_error_code(erp, DK4_E_INVALID_ARGUMENTS);
313   }
314   return back;
315   /* ----- +getnameinfo */
316 #else
317   /* +++++ -getnameinfo */
318   wchar_t		 hbuf[64];
319   wchar_t		 pbuf[64];
320   struct sockaddr_in	*psoin4;
321 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
322   struct sockaddr_in6	*psoin6;
323 #endif
324   int			 back	= DK4_SOCKET_RESULT_FAILED;
325   int			 hpah	= 0;
326   int			 res;
327   unsigned short	 us;
328 #if	DK4_USE_ASSERT
329   assert(NULL != dptr);
330   assert(NULL != saptr);
331   assert(0 < dsz);
332   assert(0 < sasz);
333 #endif
334   if ((NULL != dptr) && (0 < dsz)) { *dptr = L'\0'; }
335   if ((NULL != dptr) && (NULL != saptr) && (0 < dsz) && (0 < sasz))  {
336     switch (afam) {
337       case AF_INET : {
338         psoin4 = (struct sockaddr_in *)saptr;
339 	us = psoin4->sin_port;
340 	us = dk4socket_ntohs(us);
341 	res = dk4ma_write_wc_decimal_unsigned(
342 	  pbuf, sizeof(pbuf), (dk4_um_t)us, 0, erp
343 	);
344 	if (0 != res) {
345 	  res = dk4socket_wc_inet_ntop(
346 	   hbuf, sizeof(hbuf), AF_INET, &(psoin4->sin_addr), erp
347 	  );
348 	  if (DK4_SOCKET_RESULT_SUCCESS == res) {
349 	    hpah = 1;
350 	  }
351 	}
352       } break;
353 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
354       case AF_INET6 : {
355         psoin6 = (struct sockaddr_in6 *)saptr;
356 	us = psoin6->sin6_port;
357 	us = dk4socket_ntohs(us);
358 	res = dk4ma_write_wc_decimal_unsigned(
359 	  pbuf, sizeof(pbuf), (dk4_um_t)us, 0, erp
360 	);
361 	if (0 != res) {
362 	  res = dk4socket_wc_inet_ntop(
363 	    hbuf, sizeof(hbuf), AF_INET6, &(psoin6->sin6_addr), erp
364 	  );
365 	  if (DK4_SOCKET_RESULT_SUCCESS == res) {
366 	    hpah = 1;
367 	  }
368 	}
369       } break;
370 #endif
371       default : {
372         dk4error_set_simple_error_code(erp, DK4_E_INVALID_ARGUMENTS);
373       } break;
374     }
375     if (0 != hpah) {
376       if (0 != dk4strw_cpy_s(dptr, dsz, pbuf, erp)) {
377         if (0 != dk4strw_cat_s(dptr, dsz, dk4socket_wc_kw[0], erp)) {
378 	  if (0 != dk4strw_cat_s(dptr, dsz, hbuf, erp)) {
379 	    back = DK4_SOCKET_RESULT_SUCCESS;
380 	  }
381 	}
382       }
383     }
384   } else {
385     dk4error_set_simple_error_code(erp, DK4_E_INVALID_ARGUMENTS);
386   }
387   return back;
388   /* ----- -getnameinfo */
389 #endif
390 #else
391   DK4_UNUSED_ARG(dptr)
392   DK4_UNUSED_ARG(dsz)
393   DK4_UNUSED_ARG(afam)
394   DK4_UNUSED_ARG(saptr)
395   DK4_UNUSED_ARG(sasz)
396   dk4error_set_simple_error_code(erp, DK4_E_NOT_SUPPORTED);
397   return DK4_SOCKET_RESULT_FAILED;
398 #endif
399 }
400 
401 
402 
403 int
dk4socket_wc_sockaddr_to_text(wchar_t * dptr,size_t dsz,const dk4_sockaddr_storage_t * saptr,dk4_er_t * erp)404 dk4socket_wc_sockaddr_to_text(
405   wchar_t			*dptr,
406   size_t			 dsz,
407   const dk4_sockaddr_storage_t	*saptr,
408   dk4_er_t			*erp
409 )
410 {
411   const struct sockaddr		*soa;
412   int				 back	= DK4_SOCKET_RESULT_FAILED;
413 #if	DK4_USE_ASSERT
414   assert(NULL != dptr);
415   assert(NULL != saptr);
416   assert(0 < dsz);
417 #endif
418   if ((NULL != dptr) && (NULL != saptr) && (0 < dsz)) {
419     soa = (const struct sockaddr     *)saptr;
420     switch (soa->sa_family) {
421       case AF_INET : {
422         back = dk4socket_wc_addr_port_to_text(
423 	  dptr, dsz, AF_INET, soa, sizeof(struct sockaddr_in), erp
424 	);
425       } break;
426 #if DK4_HAVE_STRUCT_SOCKADDR_IN6
427       case AF_INET6 : {
428         back = dk4socket_wc_addr_port_to_text(
429 	  dptr, dsz, AF_INET6, soa, sizeof(struct sockaddr_in6), erp
430 	);
431       } break;
432 #endif
433       default : {
434         dk4error_set_simple_error_code(erp, DK4_E_SYNTAX);
435       } break;
436     }
437   } else {
438     dk4error_set_simple_error_code(erp, DK4_E_INVALID_ARGUMENTS);
439   }
440   return back;
441 }
442 
443