OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [gnu-src/] [gdb-7.2/] [gdb/] [ser-tcp.c] - Blame information for rev 330

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 330 jeremybenn
/* Serial interface for raw TCP connections on Un*x like systems.
2
 
3
   Copyright (C) 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2001, 2005, 2006,
4
   2007, 2008, 2009, 2010 Free Software Foundation, Inc.
5
 
6
   This file is part of GDB.
7
 
8
   This program is free software; you can redistribute it and/or modify
9
   it under the terms of the GNU General Public License as published by
10
   the Free Software Foundation; either version 3 of the License, or
11
   (at your option) any later version.
12
 
13
   This program is distributed in the hope that it will be useful,
14
   but WITHOUT ANY WARRANTY; without even the implied warranty of
15
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
   GNU General Public License for more details.
17
 
18
   You should have received a copy of the GNU General Public License
19
   along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
20
 
21
#include "defs.h"
22
#include "serial.h"
23
#include "ser-base.h"
24
#include "ser-tcp.h"
25
#include "gdbcmd.h"
26
#include "cli/cli-decode.h"
27
#include "cli/cli-setshow.h"
28
 
29
#include <sys/types.h>
30
 
31
#ifdef HAVE_SYS_FILIO_H
32
#include <sys/filio.h>  /* For FIONBIO. */
33
#endif
34
#ifdef HAVE_SYS_IOCTL_H
35
#include <sys/ioctl.h>  /* For FIONBIO. */
36
#endif
37
 
38
#include <sys/time.h>
39
 
40
#ifdef USE_WIN32API
41
#include <winsock2.h>
42
#define ETIMEDOUT WSAETIMEDOUT
43
#define close(fd) closesocket (fd)
44
#define ioctl ioctlsocket
45
#else
46
#include <netinet/in.h>
47
#include <arpa/inet.h>
48
#include <netdb.h>
49
#include <sys/socket.h>
50
#include <netinet/tcp.h>
51
#endif
52
 
53
#include <signal.h>
54
#include "gdb_string.h"
55
#include "gdb_select.h"
56
 
57
#ifndef HAVE_SOCKLEN_T
58
typedef int socklen_t;
59
#endif
60
 
61
void _initialize_ser_tcp (void);
62
 
63
/* For "set tcp" and "show tcp".  */
64
 
65
static struct cmd_list_element *tcp_set_cmdlist;
66
static struct cmd_list_element *tcp_show_cmdlist;
67
 
68
/* Whether to auto-retry refused connections.  */
69
 
70
static int tcp_auto_retry = 1;
71
 
72
/* Timeout period for connections, in seconds.  */
73
 
74
static int tcp_retry_limit = 15;
75
 
76
/* how many times per second to poll deprecated_ui_loop_hook */
77
 
78
#define POLL_INTERVAL 5
79
 
80
/* Helper function to wait a while.  If SCB is non-null, wait on its
81
   file descriptor.  Otherwise just wait on a timeout, updating *POLLS.
82
   Returns -1 on timeout or interrupt, otherwise the value of select.  */
83
 
84
static int
85
wait_for_connect (struct serial *scb, int *polls)
86
{
87
  struct timeval t;
88
  int n;
89
 
90
  /* While we wait for the connect to complete,
91
     poll the UI so it can update or the user can
92
     interrupt.  */
93
  if (deprecated_ui_loop_hook && deprecated_ui_loop_hook (0))
94
    {
95
      errno = EINTR;
96
      return -1;
97
    }
98
 
99
  /* Check for timeout.  */
100
  if (*polls > tcp_retry_limit * POLL_INTERVAL)
101
    {
102
      errno = ETIMEDOUT;
103
      return -1;
104
    }
105
 
106
  /* Back off to polling once per second after the first POLL_INTERVAL
107
     polls.  */
108
  if (*polls < POLL_INTERVAL)
109
    {
110
      t.tv_sec = 0;
111
      t.tv_usec = 1000000 / POLL_INTERVAL;
112
    }
113
  else
114
    {
115
      t.tv_sec = 1;
116
      t.tv_usec = 0;
117
    }
118
 
119
  if (scb)
120
    {
121
      fd_set rset, wset, eset;
122
 
123
      FD_ZERO (&rset);
124
      FD_SET (scb->fd, &rset);
125
      wset = rset;
126
      eset = rset;
127
 
128
      /* POSIX systems return connection success or failure by signalling
129
         wset.  Windows systems return success in wset and failure in
130
         eset.
131
 
132
         We must call select here, rather than gdb_select, because
133
         the serial structure has not yet been initialized - the
134
         MinGW select wrapper will not know that this FD refers
135
         to a socket.  */
136
      n = select (scb->fd + 1, &rset, &wset, &eset, &t);
137
    }
138
  else
139
    /* Use gdb_select here, since we have no file descriptors, and on
140
       Windows, plain select doesn't work in that case.  */
141
    n = gdb_select (0, NULL, NULL, NULL, &t);
142
 
143
  /* If we didn't time out, only count it as one poll.  */
144
  if (n > 0 || *polls < POLL_INTERVAL)
145
    (*polls)++;
146
  else
147
    (*polls) += POLL_INTERVAL;
148
 
149
  return n;
150
}
151
 
152
/* Open a tcp socket */
153
 
154
int
155
net_open (struct serial *scb, const char *name)
156
{
157
  char *port_str, hostname[100];
158
  int n, port, tmp;
159
  int use_udp;
160
  struct hostent *hostent;
161
  struct sockaddr_in sockaddr;
162
#ifdef USE_WIN32API
163
  u_long ioarg;
164
#else
165
  int ioarg;
166
#endif
167
  int polls = 0;
168
 
169
  use_udp = 0;
170
  if (strncmp (name, "udp:", 4) == 0)
171
    {
172
      use_udp = 1;
173
      name = name + 4;
174
    }
175
  else if (strncmp (name, "tcp:", 4) == 0)
176
    name = name + 4;
177
 
178
  port_str = strchr (name, ':');
179
 
180
  if (!port_str)
181
    error (_("net_open: No colon in host name!"));         /* Shouldn't ever happen */
182
 
183
  tmp = min (port_str - name, (int) sizeof hostname - 1);
184
  strncpy (hostname, name, tmp);        /* Don't want colon */
185
  hostname[tmp] = '\000';       /* Tie off host name */
186
  port = atoi (port_str + 1);
187
 
188
  /* default hostname is localhost */
189
  if (!hostname[0])
190
    strcpy (hostname, "localhost");
191
 
192
  hostent = gethostbyname (hostname);
193
  if (!hostent)
194
    {
195
      fprintf_unfiltered (gdb_stderr, "%s: unknown host\n", hostname);
196
      errno = ENOENT;
197
      return -1;
198
    }
199
 
200
  sockaddr.sin_family = PF_INET;
201
  sockaddr.sin_port = htons (port);
202
  memcpy (&sockaddr.sin_addr.s_addr, hostent->h_addr,
203
          sizeof (struct in_addr));
204
 
205
 retry:
206
 
207
  if (use_udp)
208
    scb->fd = socket (PF_INET, SOCK_DGRAM, 0);
209
  else
210
    scb->fd = socket (PF_INET, SOCK_STREAM, 0);
211
 
212
  if (scb->fd == -1)
213
    return -1;
214
 
215
  /* set socket nonblocking */
216
  ioarg = 1;
217
  ioctl (scb->fd, FIONBIO, &ioarg);
218
 
219
  /* Use Non-blocking connect.  connect() will return 0 if connected already. */
220
  n = connect (scb->fd, (struct sockaddr *) &sockaddr, sizeof (sockaddr));
221
 
222
  if (n < 0)
223
    {
224
#ifdef USE_WIN32API
225
      int err = WSAGetLastError();
226
#else
227
      int err = errno;
228
#endif
229
 
230
      /* Maybe we're waiting for the remote target to become ready to
231
         accept connections.  */
232
      if (tcp_auto_retry
233
#ifdef USE_WIN32API
234
          && err == WSAECONNREFUSED
235
#else
236
          && err == ECONNREFUSED
237
#endif
238
          && wait_for_connect (NULL, &polls) >= 0)
239
        {
240
          close (scb->fd);
241
          goto retry;
242
        }
243
 
244
      if (
245
#ifdef USE_WIN32API
246
          /* Under Windows, calling "connect" with a non-blocking socket
247
             results in WSAEWOULDBLOCK, not WSAEINPROGRESS.  */
248
          err != WSAEWOULDBLOCK
249
#else
250
          err != EINPROGRESS
251
#endif
252
          )
253
        {
254
          errno = err;
255
          net_close (scb);
256
          return -1;
257
        }
258
 
259
      /* looks like we need to wait for the connect */
260
      do
261
        {
262
          n = wait_for_connect (scb, &polls);
263
        }
264
      while (n == 0);
265
      if (n < 0)
266
        {
267
          net_close (scb);
268
          return -1;
269
        }
270
    }
271
 
272
  /* Got something.  Is it an error? */
273
  {
274
    int res, err;
275
    socklen_t len;
276
 
277
    len = sizeof (err);
278
    /* On Windows, the fourth parameter to getsockopt is a "char *";
279
       on UNIX systems it is generally "void *".  The cast to "void *"
280
       is OK everywhere, since in C "void *" can be implicitly
281
       converted to any pointer type.  */
282
    res = getsockopt (scb->fd, SOL_SOCKET, SO_ERROR, (void *) &err, &len);
283
    if (res < 0 || err)
284
      {
285
        /* Maybe the target still isn't ready to accept the connection.  */
286
        if (tcp_auto_retry
287
#ifdef USE_WIN32API
288
            && err == WSAECONNREFUSED
289
#else
290
            && err == ECONNREFUSED
291
#endif
292
            && wait_for_connect (NULL, &polls) >= 0)
293
          {
294
            close (scb->fd);
295
            goto retry;
296
          }
297
        if (err)
298
          errno = err;
299
        net_close (scb);
300
        return -1;
301
      }
302
  }
303
 
304
  /* turn off nonblocking */
305
  ioarg = 0;
306
  ioctl (scb->fd, FIONBIO, &ioarg);
307
 
308
  if (use_udp == 0)
309
    {
310
      /* Disable Nagle algorithm. Needed in some cases. */
311
      tmp = 1;
312
      setsockopt (scb->fd, IPPROTO_TCP, TCP_NODELAY,
313
                  (char *)&tmp, sizeof (tmp));
314
    }
315
 
316
#ifdef SIGPIPE
317
  /* If we don't do this, then GDB simply exits
318
     when the remote side dies.  */
319
  signal (SIGPIPE, SIG_IGN);
320
#endif
321
 
322
  return 0;
323
}
324
 
325
void
326
net_close (struct serial *scb)
327
{
328
  if (scb->fd == -1)
329
    return;
330
 
331
  close (scb->fd);
332
  scb->fd = -1;
333
}
334
 
335
int
336
net_read_prim (struct serial *scb, size_t count)
337
{
338
  return recv (scb->fd, scb->buf, count, 0);
339
}
340
 
341
int
342
net_write_prim (struct serial *scb, const void *buf, size_t count)
343
{
344
  return send (scb->fd, buf, count, 0);
345
}
346
 
347
int
348
ser_tcp_send_break (struct serial *scb)
349
{
350
  /* Send telnet IAC and BREAK characters. */
351
  return (serial_write (scb, "\377\363", 2));
352
}
353
 
354
/* Support for "set tcp" and "show tcp" commands.  */
355
 
356
static void
357
set_tcp_cmd (char *args, int from_tty)
358
{
359
  help_list (tcp_set_cmdlist, "set tcp ", -1, gdb_stdout);
360
}
361
 
362
static void
363
show_tcp_cmd (char *args, int from_tty)
364
{
365
  help_list (tcp_show_cmdlist, "show tcp ", -1, gdb_stdout);
366
}
367
 
368
 
369
void
370
_initialize_ser_tcp (void)
371
{
372
#ifdef USE_WIN32API
373
  /* Do nothing; the TCP serial operations will be initialized in
374
     ser-mingw.c.  */
375
#else
376
  struct serial_ops *ops;
377
 
378
  ops = XMALLOC (struct serial_ops);
379
  memset (ops, 0, sizeof (struct serial_ops));
380
  ops->name = "tcp";
381
  ops->next = 0;
382
  ops->open = net_open;
383
  ops->close = net_close;
384
  ops->readchar = ser_base_readchar;
385
  ops->write = ser_base_write;
386
  ops->flush_output = ser_base_flush_output;
387
  ops->flush_input = ser_base_flush_input;
388
  ops->send_break = ser_tcp_send_break;
389
  ops->go_raw = ser_base_raw;
390
  ops->get_tty_state = ser_base_get_tty_state;
391
  ops->set_tty_state = ser_base_set_tty_state;
392
  ops->print_tty_state = ser_base_print_tty_state;
393
  ops->noflush_set_tty_state = ser_base_noflush_set_tty_state;
394
  ops->setbaudrate = ser_base_setbaudrate;
395
  ops->setstopbits = ser_base_setstopbits;
396
  ops->drain_output = ser_base_drain_output;
397
  ops->async = ser_base_async;
398
  ops->read_prim = net_read_prim;
399
  ops->write_prim = net_write_prim;
400
  serial_add_interface (ops);
401
#endif /* USE_WIN32API */
402
 
403
  add_prefix_cmd ("tcp", class_maintenance, set_tcp_cmd, _("\
404
TCP protocol specific variables\n\
405
Configure variables specific to remote TCP connections"),
406
                  &tcp_set_cmdlist, "set tcp ",
407
 
408
  add_prefix_cmd ("tcp", class_maintenance, show_tcp_cmd, _("\
409
TCP protocol specific variables\n\
410
Configure variables specific to remote TCP connections"),
411
                  &tcp_show_cmdlist, "show tcp ",
412
 
413
 
414
  add_setshow_boolean_cmd ("auto-retry", class_obscure,
415
                           &tcp_auto_retry, _("\
416
Set auto-retry on socket connect"), _("\
417
Show auto-retry on socket connect"),
418
                           NULL, NULL, NULL,
419
                           &tcp_set_cmdlist, &tcp_show_cmdlist);
420
 
421
  add_setshow_uinteger_cmd ("connect-timeout", class_obscure,
422
                            &tcp_retry_limit, _("\
423
Set timeout limit for socket connection"), _("\
424
Show timeout limit for socket connection"),
425
                           NULL, NULL, NULL,
426
                           &tcp_set_cmdlist, &tcp_show_cmdlist);
427
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.