Kill off unused request() method in data-xfer interface.
[people/holger/gpxe.git] / src / core / xfer.c
1 /*
2  * Copyright (C) 2007 Michael Brown <mbrown@fensystems.co.uk>.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License as
6  * published by the Free Software Foundation; either version 2 of the
7  * License, or any later version.
8  *
9  * This program is distributed in the hope that it will be useful, but
10  * WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
17  */
18
19 #include <string.h>
20 #include <stdio.h>
21 #include <errno.h>
22 #include <gpxe/xfer.h>
23
24 /** @file
25  *
26  * Data transfer interfaces
27  *
28  */
29
30 /**
31  * Close data transfer interface
32  *
33  * @v xfer              Data transfer interface
34  * @v rc                Reason for close
35  */
36 void xfer_close ( struct xfer_interface *xfer, int rc ) {
37         struct xfer_interface *dest = xfer_get_dest ( xfer );
38
39         DBGC ( xfer, "XFER %p->%p close\n", xfer, dest );
40
41         dest->op->close ( dest, rc );
42         xfer_unplug ( xfer );
43         xfer_put ( dest );
44 }
45
46 /**
47  * Send redirection event
48  *
49  * @v xfer              Data transfer interface
50  * @v type              New location type
51  * @v args              Remaining arguments depend upon location type
52  * @ret rc              Return status code
53  */
54 int xfer_vredirect ( struct xfer_interface *xfer, int type, va_list args ) {
55         struct xfer_interface *dest = xfer_get_dest ( xfer );
56         int rc;
57
58         DBGC ( xfer, "XFER %p->%p redirect\n", xfer, dest );
59
60         rc = dest->op->vredirect ( dest, type, args );
61
62         if ( rc != 0 ) {
63                 DBGC ( xfer, "XFER %p<-%p redirect: %s\n", xfer, dest,
64                        strerror ( rc ) );
65         }
66         xfer_put ( dest );
67         return rc;
68 }
69
70 /**
71  * Send redirection event
72  *
73  * @v xfer              Data transfer interface
74  * @v type              New location type
75  * @v ...               Remaining arguments depend upon location type
76  * @ret rc              Return status code
77  */
78 int xfer_redirect ( struct xfer_interface *xfer, int type, ... ) {
79         va_list args;
80         int rc;
81
82         va_start ( args, type );
83         rc = xfer_vredirect ( xfer, type, args );
84         va_end ( args );
85         return rc;
86 }
87
88 /**
89  * Seek to position
90  *
91  * @v xfer              Data transfer interface
92  * @v offset            Offset to new position
93  * @v whence            Basis for new position
94  * @ret rc              Return status code
95  */
96 int xfer_seek ( struct xfer_interface *xfer, off_t offset, int whence ) {
97         struct xfer_interface *dest = xfer_get_dest ( xfer );
98         int rc;
99
100         DBGC ( xfer, "XFER %p->%p seek %s+%ld\n", xfer, dest,
101                whence_text ( whence ), offset );
102
103         rc = dest->op->seek ( dest, offset, whence );
104
105         if ( rc != 0 ) {
106                 DBGC ( xfer, "XFER %p<-%p seek: %s\n", xfer, dest,
107                        strerror ( rc ) );
108         }
109         xfer_put ( dest );
110         return rc;
111 }
112
113 /**
114  * Test to see if interface is ready to accept data
115  *
116  * @v xfer              Data transfer interface
117  * @ret rc              Return status code
118  *
119  * This test is optional; the data transfer interface may wish that it
120  * does not yet wish to accept data, but cannot prevent attempts to
121  * deliver data to it.
122  */
123 int xfer_ready ( struct xfer_interface *xfer ) {
124         return xfer_seek ( xfer, 0, SEEK_CUR );
125 }
126
127 /**
128  * Allocate I/O buffer
129  *
130  * @v xfer              Data transfer interface
131  * @v len               I/O buffer payload length
132  * @ret iobuf           I/O buffer
133  */
134 struct io_buffer * xfer_alloc_iob ( struct xfer_interface *xfer, size_t len ) {
135         struct xfer_interface *dest = xfer_get_dest ( xfer );
136         struct io_buffer *iobuf;
137
138         DBGC ( xfer, "XFER %p->%p alloc_iob %zd\n", xfer, dest, len );
139
140         iobuf = dest->op->alloc_iob ( dest, len );
141
142         if ( ! iobuf ) {
143                 DBGC ( xfer, "XFER %p<-%p alloc_iob failed\n", xfer, dest );
144         }
145         xfer_put ( dest );
146         return iobuf;
147 }
148
149 /**
150  * Deliver datagram as I/O buffer with metadata
151  *
152  * @v xfer              Data transfer interface
153  * @v iobuf             Datagram I/O buffer
154  * @v meta              Data transfer metadata, or NULL
155  * @ret rc              Return status code
156  */
157 int xfer_deliver_iob_meta ( struct xfer_interface *xfer,
158                             struct io_buffer *iobuf,
159                             struct xfer_metadata *meta ) {
160         struct xfer_interface *dest = xfer_get_dest ( xfer );
161         int rc;
162
163         DBGC ( xfer, "XFER %p->%p deliver_iob %zd\n", xfer, dest,
164                iob_len ( iobuf ) );
165
166         rc = dest->op->deliver_iob ( dest, iobuf, meta );
167
168         if ( rc != 0 ) {
169                 DBGC ( xfer, "XFER %p<-%p deliver_iob: %s\n", xfer, dest,
170                        strerror ( rc ) );
171         }
172         xfer_put ( dest );
173         return rc;
174 }
175
176 /**
177  * Deliver datagram as I/O buffer with metadata
178  *
179  * @v xfer              Data transfer interface
180  * @v iobuf             Datagram I/O buffer
181  * @ret rc              Return status code
182  */
183 int xfer_deliver_iob ( struct xfer_interface *xfer,
184                        struct io_buffer *iobuf ) {
185         return xfer_deliver_iob_meta ( xfer, iobuf, NULL );
186 }
187
188 /**
189  * Deliver datagram as raw data
190  *
191  * @v xfer              Data transfer interface
192  * @v iobuf             Datagram I/O buffer
193  * @ret rc              Return status code
194  */
195 int xfer_deliver_raw ( struct xfer_interface *xfer,
196                        const void *data, size_t len ) {
197         struct xfer_interface *dest = xfer_get_dest ( xfer );
198         int rc;
199
200         DBGC ( xfer, "XFER %p->%p deliver_raw %p+%zd\n", xfer, dest,
201                data, len );
202
203         rc = dest->op->deliver_raw ( dest, data, len );
204
205         if ( rc != 0 ) {
206                 DBGC ( xfer, "XFER %p<-%p deliver_raw: %s\n", xfer, dest,
207                        strerror ( rc ) );
208         }
209         xfer_put ( dest );
210         return rc;
211 }
212
213 /**
214  * Deliver formatted string
215  *
216  * @v xfer              Data transfer interface
217  * @v format            Format string
218  * @v args              Arguments corresponding to the format string
219  * @ret rc              Return status code
220  */
221 int xfer_vprintf ( struct xfer_interface *xfer, const char *format,
222                    va_list args ) {
223         size_t len;
224         va_list args_tmp;
225
226         va_copy ( args_tmp, args );
227         len = vsnprintf ( NULL, 0, format, args );
228         {
229                 char buf[len + 1];
230                 vsnprintf ( buf, sizeof ( buf ), format, args_tmp );
231                 va_end ( args_tmp );
232                 return xfer_deliver_raw ( xfer, buf, len );
233         }
234 }
235
236 /**
237  * Deliver formatted string
238  *
239  * @v xfer              Data transfer interface
240  * @v format            Format string
241  * @v ...               Arguments corresponding to the format string
242  * @ret rc              Return status code
243  */
244 int xfer_printf ( struct xfer_interface *xfer, const char *format, ... ) {
245         va_list args;
246         int rc;
247
248         va_start ( args, format );
249         rc = xfer_vprintf ( xfer, format, args );
250         va_end ( args );
251         return rc;
252 }
253
254 /****************************************************************************
255  *
256  * Helper methods
257  *
258  * These functions are designed to be used as methods in the
259  * xfer_interface_operations table.
260  *
261  */
262
263 /**
264  * Ignore close() event
265  *
266  * @v xfer              Data transfer interface
267  * @v rc                Reason for close
268  */
269 void ignore_xfer_close ( struct xfer_interface *xfer __unused,
270                          int rc __unused ) {
271         /* Nothing to do */
272 }
273
274 /**
275  * Ignore vredirect() event
276  *
277  * @v xfer              Data transfer interface
278  * @v type              New location type
279  * @v args              Remaining arguments depend upon location type
280  * @ret rc              Return status code
281  */
282 int ignore_xfer_vredirect ( struct xfer_interface *xfer __unused,
283                             int type __unused, va_list args __unused ) {
284         return 0;
285 }
286
287 /**
288  * Ignore seek() event
289  *
290  * @v xfer              Data transfer interface
291  * @v offset            Offset to new position
292  * @v whence            Basis for new position
293  * @ret rc              Return status code
294  */
295 int ignore_xfer_seek ( struct xfer_interface *xfer __unused,
296                        off_t offset __unused, int whence __unused ) {
297         return 0;
298 }
299
300 /**
301  * Allocate I/O buffer
302  *
303  * @v xfer              Data transfer interface
304  * @v len               I/O buffer payload length
305  * @ret iobuf           I/O buffer
306  */
307 struct io_buffer *
308 default_xfer_alloc_iob ( struct xfer_interface *xfer __unused, size_t len ) {
309         return alloc_iob ( len );
310 }
311
312 /**
313  * Deliver datagram as raw data
314  *
315  * @v xfer              Data transfer interface
316  * @v iobuf             Datagram I/O buffer
317  * @v meta              Data transfer metadata
318  * @ret rc              Return status code
319  *
320  * This function is intended to be used as the deliver() method for
321  * data transfer interfaces that prefer to handle raw data.
322  */
323 int xfer_deliver_as_raw ( struct xfer_interface *xfer,
324                           struct io_buffer *iobuf,
325                           struct xfer_metadata *meta __unused ) {
326         int rc;
327
328         rc = xfer->op->deliver_raw ( xfer, iobuf->data, iob_len ( iobuf ) );
329         free_iob ( iobuf );
330         return rc;
331 }
332
333 /**
334  * Deliver datagram as I/O buffer
335  *
336  * @v xfer              Data transfer interface
337  * @v data              Data buffer
338  * @v len               Length of data buffer
339  * @ret rc              Return status code
340  *
341  * This function is intended to be used as the deliver_raw() method
342  * for data transfer interfaces that prefer to handle I/O buffers.
343  */
344 int xfer_deliver_as_iob ( struct xfer_interface *xfer,
345                           const void *data, size_t len ) {
346         struct io_buffer *iobuf;
347
348         iobuf = xfer->op->alloc_iob ( xfer, len );
349         if ( ! iobuf )
350                 return -ENOMEM;
351
352         memcpy ( iob_put ( iobuf, len ), data, len );
353         return xfer->op->deliver_iob ( xfer, iobuf, NULL );
354 }
355
356 /**
357  * Ignore datagram as raw data event
358  *
359  * @v xfer              Data transfer interface
360  * @v data              Data buffer
361  * @v len               Length of data buffer
362  * @ret rc              Return status code
363  */
364 int ignore_xfer_deliver_raw ( struct xfer_interface *xfer,
365                               const void *data __unused, size_t len ) {
366         DBGC ( xfer, "XFER %p %zd bytes delivered %s\n", xfer, len,
367                ( ( xfer == &null_xfer ) ?
368                  "before connection" : "after termination" ) );
369         return 0;
370 }
371
372 /** Null data transfer interface operations */
373 struct xfer_interface_operations null_xfer_ops = {
374         .close          = ignore_xfer_close,
375         .vredirect      = ignore_xfer_vredirect,
376         .seek           = ignore_xfer_seek,
377         .alloc_iob      = default_xfer_alloc_iob,
378         .deliver_iob    = xfer_deliver_as_raw,
379         .deliver_raw    = ignore_xfer_deliver_raw,
380 };
381
382 /**
383  * Null data transfer interface
384  *
385  * This is the interface to which data transfer interfaces are
386  * connected when unplugged.  It will never generate messages, and
387  * will silently absorb all received messages.
388  */
389 struct xfer_interface null_xfer = {
390         .intf = {
391                 .dest = &null_xfer.intf,
392                 .refcnt = NULL,
393         },
394         .op = &null_xfer_ops,
395 };