sendto.c revision d7ce700605e1af0e455e31ec11f19ff21d26b525
1/** @file
2  Implement the sendto API.
3
4  Copyright (c) 2011, Intel Corporation
5  All rights reserved. This program and the accompanying materials
6  are licensed and made available under the terms and conditions of the BSD License
7  which accompanies this distribution.  The full text of the license may be found at
8  http://opensource.org/licenses/bsd-license.php
9
10  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
12
13**/
14
15#include <SocketInternals.h>
16
17
18/**
19  Send data using a network connection.
20
21  The ::send routine queues data to the network for transmission.
22  The
23  <a href="http://pubs.opengroup.org/onlinepubs/9699919799/functions/send.html">POSIX</a>
24  documentation is available online.
25
26  @param [in] s         Socket file descriptor returned from ::socket.
27
28  @param [in] buffer    Address of a buffer containing the data to send.
29
30  @param [in] length    Length of the buffer in bytes.
31
32  @param [in] flags     Message control flags
33
34  @param [in] to        Remote system address
35
36  @param [in] tolen     Length of remote system address structure
37
38  @returns    ::send returns the number of data bytes that were
39              sent and -1 when an error occurs.  In the case of
40              an error, errno contains more details.
41
42 **/
43ssize_t
44sendto (
45  int s,
46  const void * buffer,
47  size_t length,
48  int flags,
49  const struct sockaddr * to,
50  socklen_t tolen
51  )
52{
53  ssize_t LengthInBytes;
54  CONST UINT8 * pData;
55  struct __filedes * pDescriptor;
56  EFI_SOCKET_PROTOCOL * pSocketProtocol;
57  EFI_STATUS Status;
58
59  //
60  //  Assume failure
61  //
62  LengthInBytes = -1;
63
64  //
65  //  Locate the context for this socket
66  //
67  pSocketProtocol = BslFdToSocketProtocol ( s,
68                                            &pDescriptor,
69                                            &errno );
70  if ( NULL != pSocketProtocol ) {
71    //
72    //  Send the data using the socket
73    //
74    pData = buffer;
75    do {
76      errno = 0;
77      Status = pSocketProtocol->pfnSend ( pSocketProtocol,
78                                          flags,
79                                          length,
80                                          pData,
81                                          (size_t *)&LengthInBytes,
82                                          to,
83                                          tolen,
84                                          &errno );
85      if ( EFI_ERROR ( Status )) {
86        LengthInBytes = -1;
87        break;
88      }
89
90      //
91      //  Account for the data sent
92      //
93      pData += LengthInBytes;
94      length -= LengthInBytes;
95      // TODO: Add non-blocking check
96    } while (( 0 != length ) && ( EFI_NOT_READY == Status ));
97  }
98
99  //
100  //  Return the number of data bytes sent, -1 for errors
101  //
102  return (INT32)LengthInBytes;
103}
104