Version 5.0.11
[yaz-moved-to-github.git] / src / zoom-socket.c
1 /* This file is part of the YAZ toolkit.
2  * Copyright (C) Index Data
3  * See the file LICENSE for details.
4  */
5 /**
6  * \file zoom-socket.c
7  * \brief Implements ZOOM C socket interface.
8  */
9 #if HAVE_CONFIG_H
10 #include <config.h>
11 #endif
12
13 #include <assert.h>
14 #include <string.h>
15 #include <errno.h>
16 #include <yaz/zoom.h>
17
18 #include <yaz/log.h>
19 #include <yaz/xmalloc.h>
20
21 #if HAVE_SYS_TYPES_H
22 #include <sys/types.h>
23 #endif
24 #if HAVE_SYS_TIME_H
25 #include <sys/time.h>
26 #endif
27
28 #include <yaz/poll.h>
29
30 ZOOM_API(int)
31     ZOOM_event_sys_yaz_poll(int no, ZOOM_connection *cs)
32 {
33     struct yaz_poll_fd *yp = (struct yaz_poll_fd *) xmalloc(sizeof(*yp) * no);
34     int i, r;
35     int nfds = 0;
36     int timeout = 30;
37
38     for (i = 0; i < no; i++)
39     {
40         ZOOM_connection c = cs[i];
41         int fd, mask;
42
43         if (!c)
44             continue;
45         fd = ZOOM_connection_get_socket(c);
46         mask = ZOOM_connection_get_mask(c);
47         timeout = ZOOM_connection_get_timeout(c);
48
49         if (fd == -1)
50             continue;
51         if (mask)
52         {
53             enum yaz_poll_mask input_mask = yaz_poll_none;
54
55             if (mask & ZOOM_SELECT_READ)
56                 yaz_poll_add(input_mask, yaz_poll_read);
57             if (mask & ZOOM_SELECT_WRITE)
58                 yaz_poll_add(input_mask, yaz_poll_write);
59             if (mask & ZOOM_SELECT_EXCEPT)
60                 yaz_poll_add(input_mask, yaz_poll_except);
61             yp[nfds].fd = fd;
62             yp[nfds].input_mask = input_mask;
63             yp[nfds].client_data = c;
64             nfds++;
65         }
66     }
67     if (nfds == 0)
68     {
69         xfree(yp);
70         return 0;
71     }
72     r = yaz_poll(yp, nfds, timeout, 0);
73     if (r >= 0)
74     {
75         for (i = 0; i < nfds; i++)
76         {
77             ZOOM_connection c = (ZOOM_connection) yp[i].client_data;
78             enum yaz_poll_mask output_mask = yp[i].output_mask;
79             if (output_mask & yaz_poll_timeout)
80                 ZOOM_connection_fire_event_timeout(c);
81             else
82             {
83                 int mask = 0;
84                 if (output_mask & yaz_poll_read)
85                     mask += ZOOM_SELECT_READ;
86                 if (output_mask & yaz_poll_write)
87                     mask += ZOOM_SELECT_WRITE;
88                 if (output_mask & yaz_poll_except)
89                     mask += ZOOM_SELECT_EXCEPT;
90                 ZOOM_connection_fire_event_socket(c, mask);
91             }
92         }
93     }
94     xfree(yp);
95     return r;
96 }
97
98 ZOOM_API(int)
99     ZOOM_event(int no, ZOOM_connection *cs)
100 {
101     int r;
102
103     r = ZOOM_event_nonblock(no, cs);
104     if (r)
105         return r;
106     while (ZOOM_event_sys_yaz_poll(no, cs) < 0 && errno == EINTR)
107         ;
108     return ZOOM_event_nonblock(no, cs);
109 }
110
111 /*
112  * Local variables:
113  * c-basic-offset: 4
114  * c-file-style: "Stroustrup"
115  * indent-tabs-mode: nil
116  * End:
117  * vim: shiftwidth=4 tabstop=8 expandtab
118  */
119