-add Networkbrowser and Mountmanager to easy browse network for networkdevices and...
[enigma2-plugins.git] / networkbrowser / src / lib / range.c
1 /*###########################################################################
2 #
3 # written by :  Stephen J. Friedl
4 #               Software Consultant
5 #               steve@unixwiz.net
6 #
7 # Copyright (C) 2007 - 2008 by
8 # nixkoenner <nixkoenner@newnigma2.to>
9 # License: GPL
10 #
11 # This program is free software; you can redistribute it and/or modify
12 # it under the terms of the GNU General Public License as published by
13 # the Free Software Foundation; either version 2 of the License, or
14 # (at your option) any later version.
15 #
16 # This program is distributed in the hope that it will be useful,
17 # but WITHOUT ANY WARRANTY; without even the implied warranty of
18 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 # GNU General Public License for more details.
20 #
21 # You should have received a copy of the GNU General Public License
22 # along with this program; if not, write to the Free Software
23 # Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 #
25 ###########################################################################*/
26
27 #include <stdio.h>
28 #include <ctype.h>
29 #include <sys/types.h>
30 #include <sys/socket.h>
31 #include <netinet/in.h>
32 #include <arpa/inet.h>
33 #include "range.h"
34 #include <string.h>
35 #include <stdlib.h>
36 #include "errors.h"
37
38 #ifndef INADDR_NONE
39 # define INADDR_NONE (in_addr_t)-1
40 #endif
41
42 extern int quiet;
43
44 /* is_ip checks if supplied string is an ip address in dotted-decimal
45    notation, and fills both members of range structure with its numerical value
46    (host byte order)/ Returns 1 on success, 0 on failure */
47 int is_ip(char* string, struct ip_range* range) {
48         unsigned long addr;
49
50         addr = inet_addr(string);
51         if(addr != INADDR_NONE) {
52                 range->start_ip = ntohl(addr);
53                 range->end_ip   = ntohl(addr);
54                 return 1;
55         } else return 0;
56 }; 
57
58 /* is_range1 checks if supplied string is an IP address range in
59    form xxx.xxx.xxx.xxx/xx (as in 192.168.1.2/24) and fills
60    range structure with start and end ip addresses of the interval.
61    Returns 1 on success, 0 on failure */
62 int is_range1(char* string, struct ip_range* range) {
63         char* separator;
64         unsigned long mask;
65         char* ip;
66
67         if((ip = (char *)malloc(strlen(string)+1))==NULL) 
68                 err_die("Malloc failed", quiet);
69
70         if (strlen(string)>19) return 0;
71         if((separator=(char*)strchr(string,'/'))) {
72                 separator++;
73                 mask=atoi(separator);
74                 if(mask<=0 || mask>32) return 0;
75                 strcpy(ip, string);
76                 ip[abs(string-separator)-1]=0;
77                 if((range->start_ip=inet_addr(ip)) == INADDR_NONE) return 0;
78 /*              mask=((1<<mask)-1)<<(sizeof(mask)*8-mask); */
79                 if (mask == 32)
80                         mask = ~0;
81                 else
82                         mask=((1<<mask)-1)<<(sizeof(mask)*8-mask);
83
84                 range->start_ip=ntohl(range->start_ip); // We store ips in host byte order
85                 range->start_ip &= mask;
86                 range->end_ip = range->start_ip | ( ~ mask);
87                 free(ip);
88                 return 1;
89         }
90         free(ip);
91         return 0;
92 };
93
94
95 /* next_address function writes next ip address in range after prev_addr to
96    structure pointed by next_addr. Returns 1 if next ip found and 0 otherwise */ 
97 int next_address(const struct ip_range* range, const struct in_addr* prev_addr, 
98                  struct in_addr* next_addr) {
99         unsigned long pa; // previous address, host byte order
100         
101         if(prev_addr) {
102                 pa = ntohl(prev_addr->s_addr);
103                 if(pa < range->end_ip) {
104                         next_addr->s_addr=htonl(++pa); 
105                         return 1;
106                 } else return 0;
107         } else {
108                 next_addr->s_addr=htonl(range->start_ip);
109                 return 1;
110         };
111 };
112         
113 /* is_range2 checks if supplied string is an IP address range in
114    form xxx.xxx.xxx.xxx-xxx (as in 192.168.1.2-15) and fills
115    range structure with start and end ip addresses of the interval.
116    Returns 1 on success, 0 on failure */
117 int is_range2(char* string, struct ip_range* range) {
118         unsigned long last_octet; /*last octet of last ip in range*/
119         char* separator;
120         unsigned long addr;
121         char* ip;
122
123         if((ip = (char *)malloc(strlen(string)+1))==NULL) 
124                 err_die("Malloc failed", quiet);
125         strcpy(ip,string);
126
127         if((separator = (char*)strchr(ip,'-'))) {
128                 *separator=0;
129                 separator++;
130                 last_octet = atoi(separator);
131                 if(last_octet<0 || last_octet > 255) {
132                         free(ip);
133                         return 0;
134                 };
135                 addr = inet_addr(ip);
136                 if(addr == INADDR_NONE) {
137                         free(ip);
138                         return 0;
139                 };
140                 range->start_ip = ntohl(addr);
141                 range->end_ip = (range->start_ip & 0xffffff00) | last_octet;
142                 if (range->end_ip < range->start_ip) { 
143                         free(ip);
144                         return 0;
145                 };
146                 free(ip);
147                 return 1;
148         }
149         free(ip);
150         return 0;
151 };
152
153 int print_range(const struct ip_range* range) {
154         struct in_addr *addr;
155         
156         if((addr = (struct in_addr*)malloc(sizeof(struct in_addr)))==NULL) 
157                 err_die("Malloc failed", quiet);
158         
159         next_address(range, 0, addr);
160         printf("%s\n",inet_ntoa(*addr));
161         
162         while(next_address(range, addr, addr)) {
163                 printf("%s\n",inet_ntoa(*addr));
164         };
165         free(addr);
166         return 0;
167 };