OSDN Git Service

2013.10.24
[uclinux-h8/uClinux-dist.git] / freeswan / lib / ttoprotoport.c
1 /*
2  * conversion from protocol/port string to protocol and port
3  * Copyright (C) 2002 Mario Strasser <mast@gmx.net>,
4  *                    Zuercher Hochschule Winterthur,
5  *
6  * This program is free software; you can redistribute it and/or modify it
7  * under the terms of the GNU General Public License as published by the
8  * Free Software Foundation; either version 2 of the License, or (at your
9  * option) any later version.  See <http://www.fsf.org/copyleft/gpl.txt>.
10  *
11  * This program is distributed in the hope that it will be useful, but
12  * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
13  * or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14  * for more details.
15  *
16  * RCSID $Id: ttoprotoport.c,v 1.1.1.1 2002-07-08 04:11:11 danield Exp $
17  */
18
19 #include "internal.h"
20 #include "freeswan.h"
21
22 /*
23  * ttoprotoport - converts from protocol/port string to protocol and port
24  */
25 err_t
26 ttoprotoport(src, src_len, proto, port)
27 char *src;              /* input string */
28 size_t src_len;         /* length of input string, use strlen() if 0 */
29 u_int8_t *proto;        /* extracted protocol number */
30 u_int16_t *port;        /* extracted port number if it exists */
31 {
32     char *end, *service_name;
33     char proto_name[16];
34     int proto_len;
35     long int l;
36     struct protoent *protocol;
37     struct servent *service;
38
39     /* get the length of the string */
40     if (!src_len) src_len = strlen(src);
41
42     /* locate delimiter '/' between protocol and port */
43     end = strchr(src, '/');
44     if (end != NULL) {
45       proto_len = end - src;
46       service_name = end + 1;
47     } else {
48       proto_len = src_len;
49       service_name = src + src_len;
50     }
51
52    /* copy protocol name*/
53     memset(proto_name, '\0', sizeof(proto_name));
54     memcpy(proto_name, src, proto_len);
55
56     /* extract protocol by trying to resolve it by name */
57     protocol = getprotobyname(proto_name);
58     if (protocol != NULL) {
59         *proto = protocol->p_proto;
60     }
61     else  /* failed, now try it by number */
62     {
63         l = strtol(proto_name, &end, 0);
64
65         if (*proto_name && *end)
66             return "<protocol> is neither a number nor a valid name";
67
68         if (l < 0 || l > 0xff)
69             return "<protocol> must be between 0 and 255";
70
71         *proto = (u_int8_t)l;
72     }
73
74     /* extract port by trying to resolve it by name */
75     service = getservbyname(service_name, NULL);
76     if (service != NULL) {
77         *port = ntohs(service->s_port);
78     }
79     else /* failed, now try it by number */
80     {
81         l = strtol(service_name, &end, 0);
82
83         if (*service_name && *end)
84             return "<port> is neither a number nor a valid name";
85
86         if (l < 0 || l > 0xffff)
87             return "<port> must be between 0 and 65535";
88
89         *port = (u_int16_t)l;
90     }
91     return NULL;
92 }
93