Annotation of embedaddon/miniupnpd/miniupnpc/src/listdevices.c, revision 1.1.1.1
1.1 misho 1: /* $Id: listdevices.c,v 1.6 2015/07/23 20:40:08 nanard Exp $ */
2: /* Project : miniupnp
3: * Author : Thomas Bernard
4: * Copyright (c) 2013-2015 Thomas Bernard
5: * This software is subject to the conditions detailed in the
6: * LICENCE file provided in this distribution. */
7:
8: #include <stdio.h>
9: #include <string.h>
10: #include <stdlib.h>
11: #ifdef _WIN32
12: #include <winsock2.h>
13: #endif /* _WIN32 */
14: #include "miniupnpc.h"
15:
16: struct upnp_dev_list {
17: struct upnp_dev_list * next;
18: char * descURL;
19: struct UPNPDev * * array;
20: size_t count;
21: size_t allocated_count;
22: };
23:
24: #define ADD_DEVICE_COUNT_STEP 16
25:
26: void add_device(struct upnp_dev_list * * list_head, struct UPNPDev * dev)
27: {
28: struct upnp_dev_list * elt;
29: size_t i;
30:
31: if(dev == NULL)
32: return;
33: for(elt = *list_head; elt != NULL; elt = elt->next) {
34: if(strcmp(elt->descURL, dev->descURL) == 0) {
35: for(i = 0; i < elt->count; i++) {
36: if (strcmp(elt->array[i]->st, dev->st) == 0 && strcmp(elt->array[i]->usn, dev->usn) == 0) {
37: return; /* already found */
38: }
39: }
40: if(elt->count >= elt->allocated_count) {
41: struct UPNPDev * * tmp;
42: elt->allocated_count += ADD_DEVICE_COUNT_STEP;
43: tmp = realloc(elt->array, elt->allocated_count * sizeof(struct UPNPDev *));
44: if(tmp == NULL) {
45: fprintf(stderr, "Failed to realloc(%p, %lu)\n", elt->array, (unsigned long)(elt->allocated_count * sizeof(struct UPNPDev *)));
46: return;
47: }
48: elt->array = tmp;
49: }
50: elt->array[elt->count++] = dev;
51: return;
52: }
53: }
54: elt = malloc(sizeof(struct upnp_dev_list));
55: if(elt == NULL) {
56: fprintf(stderr, "Failed to malloc(%lu)\n", (unsigned long)sizeof(struct upnp_dev_list));
57: return;
58: }
59: elt->next = *list_head;
60: elt->descURL = strdup(dev->descURL);
61: if(elt->descURL == NULL) {
62: fprintf(stderr, "Failed to strdup(%s)\n", dev->descURL);
63: free(elt);
64: return;
65: }
66: elt->allocated_count = ADD_DEVICE_COUNT_STEP;
67: elt->array = malloc(ADD_DEVICE_COUNT_STEP * sizeof(struct UPNPDev *));
68: if(elt->array == NULL) {
69: fprintf(stderr, "Failed to malloc(%lu)\n", (unsigned long)(ADD_DEVICE_COUNT_STEP * sizeof(struct UPNPDev *)));
70: free(elt->descURL);
71: free(elt);
72: return;
73: }
74: elt->array[0] = dev;
75: elt->count = 1;
76: *list_head = elt;
77: }
78:
79: void free_device(struct upnp_dev_list * elt)
80: {
81: free(elt->descURL);
82: free(elt->array);
83: free(elt);
84: }
85:
86: int main(int argc, char * * argv)
87: {
88: const char * searched_device = NULL;
89: const char * * searched_devices = NULL;
90: const char * multicastif = 0;
91: const char * minissdpdpath = 0;
92: int ipv6 = 0;
93: unsigned char ttl = 2;
94: int error = 0;
95: struct UPNPDev * devlist = 0;
96: struct UPNPDev * dev;
97: struct upnp_dev_list * sorted_list = NULL;
98: struct upnp_dev_list * dev_array;
99: int i;
100:
101: #ifdef _WIN32
102: WSADATA wsaData;
103: int nResult = WSAStartup(MAKEWORD(2,2), &wsaData);
104: if(nResult != NO_ERROR)
105: {
106: fprintf(stderr, "WSAStartup() failed.\n");
107: return -1;
108: }
109: #endif
110:
111: for(i = 1; i < argc; i++) {
112: if(strcmp(argv[i], "-6") == 0)
113: ipv6 = 1;
114: else if(strcmp(argv[i], "-d") == 0) {
115: if(++i >= argc) {
116: fprintf(stderr, "%s option needs one argument\n", "-d");
117: return 1;
118: }
119: searched_device = argv[i];
120: } else if(strcmp(argv[i], "-t") == 0) {
121: if(++i >= argc) {
122: fprintf(stderr, "%s option needs one argument\n", "-t");
123: return 1;
124: }
125: ttl = (unsigned char)atoi(argv[i]);
126: } else if(strcmp(argv[i], "-l") == 0) {
127: if(++i >= argc) {
128: fprintf(stderr, "-l option needs at least one argument\n");
129: return 1;
130: }
131: searched_devices = (const char * *)(argv + i);
132: break;
133: } else if(strcmp(argv[i], "-m") == 0) {
134: if(++i >= argc) {
135: fprintf(stderr, "-m option needs one argument\n");
136: return 1;
137: }
138: multicastif = argv[i];
139: } else {
140: printf("usage : %s [options] [-l <device1> <device2> ...]\n", argv[0]);
141: printf("options :\n");
142: printf(" -6 : use IPv6\n");
143: printf(" -m address/ifname : network interface to use for multicast\n");
144: printf(" -d <device string> : search only for this type of device\n");
145: printf(" -l <device1> <device2> ... : search only for theses types of device\n");
146: printf(" -t ttl : set multicast TTL. Default value is 2.\n");
147: printf(" -h : this help\n");
148: return 1;
149: }
150: }
151:
152: if(searched_device) {
153: printf("searching UPnP device type %s\n", searched_device);
154: devlist = upnpDiscoverDevice(searched_device,
155: 2000, multicastif, minissdpdpath,
156: 0/*localport*/, ipv6, ttl, &error);
157: } else if(searched_devices) {
158: printf("searching UPnP device types :\n");
159: for(i = 0; searched_devices[i]; i++)
160: printf("\t%s\n", searched_devices[i]);
161: devlist = upnpDiscoverDevices(searched_devices,
162: 2000, multicastif, minissdpdpath,
163: 0/*localport*/, ipv6, ttl, &error, 1);
164: } else {
165: printf("searching all UPnP devices\n");
166: devlist = upnpDiscoverAll(2000, multicastif, minissdpdpath,
167: 0/*localport*/, ipv6, ttl, &error);
168: }
169: if(devlist) {
170: for(dev = devlist, i = 1; dev != NULL; dev = dev->pNext, i++) {
171: printf("%3d: %-48s\n", i, dev->st);
172: printf(" %s\n", dev->descURL);
173: printf(" %s\n", dev->usn);
174: add_device(&sorted_list, dev);
175: }
176: putchar('\n');
177: for (dev_array = sorted_list; dev_array != NULL ; dev_array = dev_array->next) {
178: printf("%s :\n", dev_array->descURL);
179: for(i = 0; (unsigned)i < dev_array->count; i++) {
180: printf("%2d: %s\n", i+1, dev_array->array[i]->st);
181: printf(" %s\n", dev_array->array[i]->usn);
182: }
183: putchar('\n');
184: }
185: freeUPNPDevlist(devlist);
186: while(sorted_list != NULL) {
187: dev_array = sorted_list;
188: sorted_list = sorted_list->next;
189: free_device(dev_array);
190: }
191: } else {
192: printf("no device found.\n");
193: }
194:
195: return 0;
196: }
197:
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>