~ubuntu-branches/ubuntu/trusty/libupnp4/trusty

« back to all changes in this revision

Viewing changes to upnp/src/genlib/net/http/httpreadwrite.c

  • Committer: Bazaar Package Importer
  • Author(s): Nick Leverton
  • Date: 2010-03-08 18:26:14 UTC
  • mfrom: (1.1.1 upstream)
  • Revision ID: james.westby@ubuntu.com-20100308182614-y3j47t5ddhrza6be
Tags: 1.8.0~svn20090313-1
* ACK NMU (thanks to gregor herrmann and Stefan Potyra).
* Pull from svn, see upstream changes.gz for details
  (Closes: #492160, FTBFS on GNU/kFreeBSD, thanks to Petr Salinger).
* Update Sections and general Policy to 3.8.4
* Use debhelper 7 dh instead of dbs
* Generate and update symbols file
* Rename libs to libupnp4, libixml4 and libthreadutil4, to allow
  co-installing libupnp3 and libupnp4.
* New patch 04-string-access-functions.patch: add _strget_ accessors
  to API, to avoid remembering to call UpnpString_get_String in clients.
* New patch 05-const-tidyup.patch for a few constness fixes.
* Upstream patch 06-patch-statevar-query.patch for missing CRNL.
* New patch 07-neaten-debug.patch to improve debug readability
* New patch 08-renewals-sid.patch to fix autorenewals.
* New patch 09-update-doc.patch to generate up to date -doc package.
* New patch 10-upnpinit-ntoa.patch to replace inet_ntoa by inet_ntop.

Show diffs side-by-side

added added

removed removed

Lines of Context:
50
50
#include "uri.h"
51
51
#include "statcodes.h"
52
52
#include "sock.h"
 
53
#include "UpnpInet.h"
53
54
#include "webserver.h"
54
55
 
55
56
 
66
67
 
67
68
 
68
69
#ifdef WIN32
69
 
        #include <winsock2.h>
70
70
        #include <malloc.h>
71
71
#else
72
72
        #include <arpa/inet.h>
73
73
        #include <fcntl.h>
74
 
        #include <netinet/in.h>
75
74
        #include <sys/types.h>
76
75
        #include <sys/socket.h>
77
76
        #include <sys/time.h>
205
204
}
206
205
 
207
206
 
208
 
/************************************************************************
209
 
 * Function: http_RecvMessage
 
207
/*!
 
208
 * \brief Get the data on the socket and take actions based on the read data to
 
209
 * modify the parser objects buffer.
 
210
 *
 
211
 * If an error is reported while parsing the data, the error code is passed in
 
212
 * the http_errr_code parameter.
210
213
 *
211
214
 * Parameters:
212
215
 *      IN SOCKINFO *info;                      Socket information object
215
218
 *      IN OUT int* timeout_secs;               time out
216
219
 *      OUT int* http_error_code;               HTTP error code returned
217
220
 *
218
 
 * Description:
219
 
 *      Get the data on the socket and take actions based on the read data
220
 
 *      to modify the parser objects buffer. If an error is reported while
221
 
 *      parsing the data, the error code is passed in the http_errr_code
222
 
 *      parameter
223
 
 *
224
 
 * Returns:
 
221
 * \return
 
222
 *       UPNP_E_SUCCESS
225
223
 *       UPNP_E_BAD_HTTPMSG
226
 
 *       UPNP_E_SUCCESS
227
 
 ************************************************************************/
228
 
int
229
 
http_RecvMessage( IN SOCKINFO * info,
230
 
                  OUT http_parser_t * parser,
231
 
                  IN http_method_t request_method,
232
 
                  IN OUT int *timeout_secs,
233
 
                  OUT int *http_error_code )
 
224
 */
 
225
int http_RecvMessage(
 
226
        IN SOCKINFO *info,
 
227
        OUT http_parser_t *parser,
 
228
        IN http_method_t request_method,
 
229
        IN OUT int *timeout_secs,
 
230
        OUT int *http_error_code)
234
231
{
235
 
    parse_status_t status;
236
 
    int num_read;
237
 
    xboolean ok_on_close = FALSE;
238
 
    char buf[2 * 1024];
239
 
 
240
 
    if( request_method == HTTPMETHOD_UNKNOWN ) {
241
 
        parser_request_init( parser );
242
 
    } else {
243
 
        parser_response_init( parser, request_method );
244
 
    }
245
 
 
246
 
    while( TRUE ) {
247
 
        num_read = sock_read( info, buf, sizeof( buf ), timeout_secs );
248
 
        if( num_read > 0 ) {
249
 
            // got data
250
 
            status = parser_append( parser, buf, num_read );
251
 
 
252
 
            if( status == PARSE_SUCCESS ) {
253
 
                UpnpPrintf( UPNP_INFO, HTTP, __FILE__, __LINE__,
254
 
                    "<<< (RECVD) <<<\n%s\n-----------------\n",
255
 
                    parser->msg.msg.buf );
256
 
                    print_http_headers( &parser->msg );
257
 
 
258
 
                if( parser->content_length >
259
 
                    ( unsigned int )g_maxContentLength ) {
260
 
                    *http_error_code = HTTP_REQ_ENTITY_TOO_LARGE;
261
 
                    return UPNP_E_OUTOF_BOUNDS;
262
 
                }
263
 
 
264
 
                return 0;
265
 
            } else if( status == PARSE_FAILURE ) {
266
 
                *http_error_code = parser->http_error_code;
267
 
                return UPNP_E_BAD_HTTPMSG;
268
 
            } else if( status == PARSE_INCOMPLETE_ENTITY ) {
269
 
                // read until close
270
 
                ok_on_close = TRUE;
271
 
            } else if( status == PARSE_CONTINUE_1 ) //Web post request. murari
272
 
            {
273
 
                return PARSE_SUCCESS;
274
 
            }
275
 
        } else if( num_read == 0 ) {
276
 
            if( ok_on_close ) {
277
 
                UpnpPrintf( UPNP_INFO, HTTP, __FILE__, __LINE__,
278
 
                    "<<< (RECVD) <<<\n%s\n-----------------\n",
279
 
                    parser->msg.msg.buf );
280
 
                    print_http_headers( &parser->msg );
281
 
 
282
 
                    return 0;
283
 
            } else {
284
 
                // partial msg
285
 
                *http_error_code = HTTP_BAD_REQUEST;    // or response
286
 
                return UPNP_E_BAD_HTTPMSG;
287
 
            }
288
 
        } else {
289
 
            *http_error_code = parser->http_error_code;
290
 
            return num_read;
291
 
        }
292
 
    }
 
232
        int ret = UPNP_E_SUCCESS;
 
233
        int line = 0;
 
234
        parse_status_t status;
 
235
        int num_read;
 
236
        xboolean ok_on_close = FALSE;
 
237
        char buf[2 * 1024];
 
238
 
 
239
        if (request_method == HTTPMETHOD_UNKNOWN) {
 
240
                parser_request_init(parser);
 
241
        } else {
 
242
                parser_response_init(parser, request_method);
 
243
        }
 
244
 
 
245
        while (TRUE) {
 
246
                num_read = sock_read(info, buf, sizeof buf, timeout_secs);
 
247
                if (num_read > 0) {
 
248
                        // got data
 
249
                        status = parser_append(parser, buf, num_read);
 
250
                        if (status == PARSE_SUCCESS) {
 
251
                                UpnpPrintf( UPNP_INFO, HTTP, __FILE__, __LINE__,
 
252
                                        "<<< (RECVD) <<<\n%s\n-----------------\n",
 
253
                                        parser->msg.msg.buf );
 
254
                                print_http_headers( &parser->msg );
 
255
                                if (parser->content_length > (unsigned int)g_maxContentLength) {
 
256
                                        *http_error_code = HTTP_REQ_ENTITY_TOO_LARGE;
 
257
                                        line = __LINE__;
 
258
                                        ret = UPNP_E_OUTOF_BOUNDS;
 
259
                                        goto ExitFunction;
 
260
                                }
 
261
                                line = __LINE__;
 
262
                                ret = 0;
 
263
                                goto ExitFunction;
 
264
                        } else if (status == PARSE_FAILURE) {
 
265
                                *http_error_code = parser->http_error_code;
 
266
                                line = __LINE__;
 
267
                                ret = UPNP_E_BAD_HTTPMSG;
 
268
                                goto ExitFunction;
 
269
                        } else if (status == PARSE_INCOMPLETE_ENTITY) {
 
270
                                // read until close
 
271
                                ok_on_close = TRUE;
 
272
                        } else if (status == PARSE_CONTINUE_1) {
 
273
                                // Web post request.
 
274
                                line = __LINE__;
 
275
                                ret = PARSE_SUCCESS;
 
276
                                goto ExitFunction;
 
277
                        }
 
278
                } else if (num_read == 0) {
 
279
                        if (ok_on_close) {
 
280
                                UpnpPrintf( UPNP_INFO, HTTP, __FILE__, __LINE__,
 
281
                                        "<<< (RECVD) <<<\n%s\n-----------------\n",
 
282
                                        parser->msg.msg.buf );
 
283
                                print_http_headers(&parser->msg);
 
284
                                line = __LINE__;
 
285
                                ret = 0;
 
286
                                goto ExitFunction;
 
287
                        } else {
 
288
                                // partial msg
 
289
                                *http_error_code = HTTP_BAD_REQUEST;    // or response
 
290
                                line = __LINE__;
 
291
                                ret = UPNP_E_BAD_HTTPMSG;
 
292
                                goto ExitFunction;
 
293
                        }
 
294
                } else {
 
295
                        *http_error_code = parser->http_error_code;
 
296
                        line = __LINE__;
 
297
                        ret = num_read;
 
298
                        goto ExitFunction;
 
299
                }
 
300
        }
 
301
 
 
302
ExitFunction:
 
303
        if (ret != UPNP_E_SUCCESS) {
 
304
                UpnpPrintf(UPNP_ALL, HTTP, __FILE__, line,
 
305
                        "(http_RecvMessage): Error %d, http_error_code = %d.\n",
 
306
                        ret,
 
307
                        *http_error_code);
 
308
        }
 
309
 
 
310
        return ret;
293
311
}
294
312
 
295
313