ucspi-ssl 0.13.00
ucspi-ssl
Loading...
Searching...
No Matches
ip6_bit.c
Go to the documentation of this file.
1
6#include "ip.h"
7#include "byte.h"
8#include "str.h"
9#include "fmt.h"
10#include "stralloc.h"
11#include "ip_bit.h"
12
13#define BITSUBSTITUTION
14
15/***
16 /fn bytetohex
17 /brief Convert a number of max 255 to hex.
18 /param decimal The decimal number.
19 /param hex The converted hex value.
20*/
21
22void bytetohex(unsigned char decimal, char hex[3])
23{
24 char* hexdigits = "0123456789ABCDEF";
25 int rest, number;
26 hex[0] = '0';
27 hex[1] = '0';
28 hex[2] = '\0';
29
30 number = decimal / 16;
31 rest = decimal % 16;
32
33 hex[0] = hexdigits[number];
34 hex[1] = hexdigits[rest];
35}
36
37static char strnum[FMT_ULONG];
38
39/***
40 /fn ip6_bitstring
41 /brief This function converts a IPv6 address into its binary representation.
42 /param out: ip6string The destination address.
43 /param in: ip6addr The source address.
44 /param in: prefix The net prefix bits (maximum 128 bits for IPv6).
45 /return -1: lack of memory; 1: non valid IPv6 address; 0: successful converted.
46*/
47
48int ip6_bitstring(stralloc *ip6string, char *ip6addr, unsigned int prefix)
49{
50 char ip6[16];
51 int bit, octettbitpos, number, shiftedvalue;
52 int i, slashpos, ip6len;
53
54#ifdef BITSUBSTITUTION
55 char subvalueforbitone[1];
56 subvalueforbitone[0] = 96; /* substitution starts from token '_' = 96 */
57#endif
58
59 ip6len = str_len(ip6addr);
60 slashpos = byte_chr(ip6addr,ip6len,'/');
61 if (!stralloc_copyb(ip6string,ip6addr,slashpos)) return -1;
62 ip6addr[slashpos] = '\0';
63
64 if (!ip6_scan(ip6addr,ip6)) return 1;
65 if (!stralloc_copys(ip6string,"")) return -1;
66
67 for (i = 0; i < 16; i++) {
68 number = (unsigned char) ip6[i];
69
70 for (octettbitpos = 7; octettbitpos >= 0; octettbitpos--) {
71 shiftedvalue = 1 << octettbitpos;
72 bit = number / shiftedvalue;
73 number = number - bit * (shiftedvalue);
74
75 if (bit) {
76#ifdef BITSUBSTITUTION
77 if (!stralloc_catb(ip6string,subvalueforbitone,1)) return -1;
78 subvalueforbitone[0]++;
79#else
80 if (!stralloc_cats(ip6string,"1")) return -1;
81#endif
82 } else
83 if (!stralloc_cats(ip6string,"0")) return -1;
84
85 prefix--;
86 if (prefix == 0) return 0;
87 }
88 }
89
90 return 1;
91}
92
93/***
94 /fn bitstring_ip6
95 /brief This function converts a bit string which is produced by ip6_bitstring()
96 into an IPv6 address. The string may start with a '^'.
97 /param in: ip6string Source string which need to be converted.
98 /param out ip6addr 0-terminated IPv6 destination address with net prefix.
99 /return -1: No memory could allocated,0: Failure,1: Success.
100*/
101
102int bitstring_ip6(stralloc *ip6addr ,stralloc *ip6string)
103{
104 int j = 0;
105 int i = 0;
106 int len, prefix, shiftedvalue;
107 int bitpos = 7;
108 int decimalnumber = 0;
109 char ip6[16] = {0};
110 char ip6compact[40] = {0};
111
112 if (!stralloc_copys(ip6addr,"")) return -1;
113 prefix = ip6string->len - 1;
114
115 if (prefix <= 0) return 1;
116 if (prefix <= 1 || prefix > 128) return 1;
117
118 if (ip6string->s[0] == '^') j = 1;
119
120 for (i = j, j = 0; i <= prefix; i++) {
121 if (ip6string->s[i] != '0') {
122 shiftedvalue = 1 << bitpos;
123 decimalnumber += shiftedvalue;
124 }
125 bitpos--;
126 if (bitpos == -1) { /* Put each converted byte into the array. */
127 if (j < 16) {
128 ip6[j] = (unsigned char) decimalnumber;
129 j++;
130 bitpos = 7;
131 decimalnumber = 0;
132 }
133 }
134 }
135
136 if (bitpos < 7) { /* Last bit was read,but the number was not converted. */
137 ip6[j] = (unsigned char) decimalnumber;
138 j++;
139 }
140
141 len = ip6_fmt(ip6compact,ip6);
142 if (!len) return 1;
143
144 if (!stralloc_copyb(ip6addr,ip6compact,len)) return -1;
145 if (!stralloc_cats(ip6addr,"/")) return -1;
146 if (!stralloc_catb(ip6addr,strnum,fmt_ulong(strnum,prefix))) return -1;
147 if (!stralloc_0(ip6addr)) return -1;
148
149 return 0;
150}
151/***
152 /fn ip6_fmt_str
153 /brief This function expands any valid IPv6 address into its full format of 16 bytes.
154 It returns the number of processed tokens on success.
155 /param src Source IPv6 address.
156 /param destination Expanded IPv6 address.
157 /return -1: No memory could allocated; 1: failure, 0: success
158*/
159
160unsigned int ip6_fmt_str(stralloc *dest, char *src)
161{
162 stralloc addr = {0};
163 char ip6[16];
164 char hexvalue[3] = {0, 0, 0};
165 int i;
166
167 if (!stralloc_copys(&addr,src)) return -1;
168 if (!stralloc_0(&addr)) return -1;
169
170 if (ip6_scan(addr.s,ip6) == 0) return 1;
171 if (!stralloc_copys(dest,"")) return -1;
172
173 for (i = 0; i < 16; i++) {
174 bytetohex((unsigned char)ip6[i],hexvalue);
175 stralloc_catb(dest,hexvalue,2);
176 if (!((i+1) % 2) && (i+1) < 16)
177 if (!stralloc_cats(dest,":")) return -1; /*Append ':' after every two bytes.*/
178 }
179 return 0;
180}
int bitstring_ip6(stralloc *ip6addr, stralloc *ip6string)
Definition: ip6_bit.c:102
void bytetohex(unsigned char decimal, char hex[3])
Definition: ip6_bit.c:22
int ip6_bitstring(stralloc *ip6string, char *ip6addr, unsigned int prefix)
Definition: ip6_bit.c:48
unsigned int ip6_fmt_str(stralloc *dest, char *src)
Definition: ip6_bit.c:160