A Discrete-Event Network Simulator
API
http-header.cc
Go to the documentation of this file.
1 /* -*- Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2015 Magister Solutions
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License version 2 as
7  * published by the Free Software Foundation;
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17  *
18  * Author: Miralem Mehic <miralem.mehic@ieee.org>
19  *
20  */
21 
22 #include <ns3/log.h>
23 #include <ns3/packet.h>
24 #include <sstream>
25 #include "http-header.h"
26 
27 NS_LOG_COMPONENT_DEFINE ("HttpHeader");
28 
29 namespace ns3 {
30 
31 NS_OBJECT_ENSURE_REGISTERED (HttpHeader);
32 
34  : Header (),
35  m_status(0),
36  m_contentType (MAIN_OBJECT),
37  m_contentLength (0)
38 {
39  NS_LOG_FUNCTION (this);
40 }
41 
42 // static
43 TypeId
45 {
46  static TypeId tid = TypeId ("ns3::HttpHeader")
47  .SetParent<Header> ()
48  .AddConstructor<HttpHeader> ()
49  ;
50  return tid;
51 }
52 
53 TypeId
55 {
56  return GetTypeId ();
57 }
58 
59 uint32_t
61 {
62  return 3 * sizeof(uint16_t) +
63  sizeof(uint32_t) +
64  sizeof(uint64_t) +
65  m_contentLength * sizeof(char);
66 }
67 
68 void
70 {
71  NS_LOG_FUNCTION (this << &start);
72 
73  start.WriteU16 (m_method);
74  start.WriteU16 (m_status);
75  start.WriteU16 (m_contentType);
76  start.WriteU32 (m_contentLength);
77  start.WriteU64 (m_size);
78 
79  NS_LOG_FUNCTION(this << "m_method: " << m_method);
80  NS_LOG_FUNCTION(this << "m_status: " << m_status);
81  NS_LOG_FUNCTION(this << "m_contentType: " << m_contentType);
82  NS_LOG_FUNCTION(this << "m_contentLength: " << m_contentLength);
83  NS_LOG_FUNCTION(this << "m_size: " << m_size);
84 
85  char tmpBuffer [m_contentLength];
86  strcpy (tmpBuffer, m_uri.c_str());
87  start.Write ((uint8_t *)tmpBuffer, m_contentLength );
88 }
89 
90 uint32_t
92 {
93  NS_LOG_FUNCTION (this << &start);
95 
96  m_method = i.ReadU16 ();
97  m_status = i.ReadU16 ();
98  m_contentType = i.ReadU16 ();
99  m_contentLength = i.ReadU32 ();
100  m_size = i.ReadU64 ();
101 
102  NS_LOG_FUNCTION(this << "m_method: " << m_method);
103  NS_LOG_FUNCTION(this << "m_status: " << m_status);
104  NS_LOG_FUNCTION(this << "m_contentType: " << m_contentType);
105  NS_LOG_FUNCTION(this << "m_contentLength: " << m_contentLength);
106  NS_LOG_FUNCTION(this << "m_size: " << m_size);
107 
108  char tmpBuffer [m_contentLength];
109  i.Read ((uint8_t*)tmpBuffer, m_contentLength);
110  m_uri = std::string(tmpBuffer).substr(0, m_contentLength);
111 
112  NS_LOG_FUNCTION(this << m_uri << m_uri.length() << m_contentLength );
113 
114  uint32_t dist = i.GetDistanceFrom (start);
115  NS_LOG_FUNCTION( this << dist << GetSerializedSize() );
116  NS_ASSERT (dist == GetSerializedSize ());
117  return dist;
118 }
119 
120 void
121 HttpHeader::Print (std::ostream &os) const
122 {
123  NS_LOG_FUNCTION (this << &os);
124  os << "(Method: " << m_method
125  << " Status: " << m_status
126  << " Content-Type: " << m_contentType
127  << " Content-Length: " << m_contentLength
128  << " URI: " << m_uri << ")";
129 }
130 
131 std::string
133 {
134  NS_LOG_FUNCTION (this);
135  std::ostringstream oss;
136  Print (oss);
137  return oss.str ();
138 }
139 
140 void
142 {
143  NS_LOG_FUNCTION (this << static_cast<uint16_t> (contentType));
144  switch (contentType)
145  {
146  case NOT_SET:
147  m_contentType = 0;
148  break;
149  case MAIN_OBJECT:
150  m_contentType = 1;
151  break;
152  case EMBEDDED_OBJECT:
153  m_contentType = 2;
154  break;
155  default:
156  NS_FATAL_ERROR ("Unknown Content-Type: " << contentType);
157  break;
158  }
159 }
160 
163 {
164  ContentType_t ret;
165  switch (m_contentType)
166  {
167  case 0:
168  ret = NOT_SET;
169  break;
170  case 1:
171  ret = MAIN_OBJECT;
172  break;
173  case 2:
174  ret = EMBEDDED_OBJECT;
175  break;
176  default:
177  NS_FATAL_ERROR ("Unknown Content-Type: " << m_contentType);
178  break;
179  }
180  return ret;
181 }
182 
183 void
184 HttpHeader::SetContentLength (uint32_t contentLength)
185 {
186  NS_LOG_FUNCTION (this << contentLength);
187  m_contentLength = contentLength;
188 }
189 
190 
191 uint32_t
193 {
194  return m_contentLength;
195 }
196 
197 
198 void
199 HttpHeader::SetSize (uint64_t size)
200 {
201  m_size = size;
202 }
203 
204 uint64_t
206 {
207  return m_size;
208 }
209 
210 void
212 {
213  NS_LOG_FUNCTION (this << status);
214  switch (status)
215  {
216  case Continue:
217  m_status = 100;
218  break;
219  case SwitchingProtocol:
220  m_status = 101;
221  break;
222  case Processing:
223  m_status = 102;
224  break;
225  case EarlyHints:
226  m_status = 103;
227  break;
228 
229  case Ok:
230  m_status = 200;
231  break;
232  case Created:
233  m_status = 201;
234  break;
235  case Accepted:
236  m_status = 202;
237  break;
239  m_status = 203;
240  break;
241  case NoContent:
242  m_status = 204;
243  break;
244  case ResetContent:
245  m_status = 205;
246  break;
247  case PartialContent:
248  m_status = 206;
249  break;
250  case MultiStatus:
251  m_status = 207;
252  break;
253  case AlreadyReported:
254  m_status = 208;
255  break;
256  case ImUsed:
257  m_status = 226;
258  break;
259 
260  case MultipleChoice:
261  m_status = 300;
262  break;
263  case MovedPermanently:
264  m_status = 301;
265  break;
266  case Found:
267  m_status = 302;
268  break;
269  case SeeOther:
270  m_status = 303;
271  break;
272  case NotModified:
273  m_status = 304;
274  break;
275  case UseProxy:
276  m_status = 305;
277  break;
278  case TemporaryRedirect:
279  m_status = 307;
280  break;
281  case PermanentRedirect:
282  m_status = 308;
283  break;
284 
285  case BadRequest:
286  m_status = 400;
287  break;
288  case Unauthorized:
289  m_status = 401;
290  break;
291  case PaymentRequired:
292  m_status = 402;
293  break;
294  case Forbidden:
295  m_status = 403;
296  break;
297  case NotFound:
298  m_status = 404;
299  break;
300  case MethodNotAllowed:
301  m_status = 405;
302  break;
303  case NotAcceptable:
304  m_status = 406;
305  break;
307  m_status = 407;
308  break;
309  case RequestTimeout:
310  m_status = 408;
311  break;
312  case Conflict:
313  m_status = 409;
314  break;
315  case Gone:
316  m_status = 410;
317  break;
318  case LengthRequired:
319  m_status = 411;
320  break;
321  case PreconditionFailed:
322  m_status = 412;
323  break;
324  case PayloadTooLarge:
325  m_status = 413;
326  break;
327  case UriTooLong:
328  m_status = 414;
329  break;
330  case UnsupportedMediaType:
331  m_status = 415;
332  break;
333  case RangeNotSatisfiable:
334  m_status = 416;
335  break;
336  case ExpectationFailed:
337  m_status = 417;
338  break;
339  case ImaTeapot:
340  m_status = 418;
341  break;
342  case MisdirectedRequest:
343  m_status = 421;
344  break;
345  case UnprocessableEntity:
346  m_status = 422;
347  break;
348  case Locked:
349  m_status = 423;
350  break;
351  case FailedDependency:
352  m_status = 424;
353  break;
354  case TooEarly:
355  m_status = 425;
356  break;
357  case UpgradeRequired:
358  m_status = 426;
359  break;
360  case PreconditionRequired:
361  m_status = 428;
362  break;
363  case TooManyRequests:
364  m_status = 429;
365  break;
367  m_status = 431;
368  break;
370  m_status = 451;
371  break;
372 
373  case InternalServerError:
374  m_status = 500;
375  break;
376  case NotImplemented:
377  m_status = 501;
378  break;
379  case BadGateway:
380  m_status = 502;
381  break;
382  case ServiceUnavailable:
383  m_status = 503;
384  break;
385  case GatewayTimeout:
386  m_status = 504;
387  break;
389  m_status = 505;
390  break;
391  case VariantAlsoNegotiates:
392  m_status = 506;
393  break;
394  case InsufficientStorage:
395  m_status = 507;
396  break;
397  case LoopDetected:
398  m_status = 508;
399  break;
400  case NotExtended:
401  m_status = 510;
402  break;
404  m_status = 511;
405  break;
406  default:
407  NS_FATAL_ERROR ("Unknown status: " << m_status);
408  break;
409  }
410 }
411 
412 
415 {
416  HttpStatus ret;
417  switch (m_status)
418  {
419  case 100:
420  ret = Continue;
421  break;
422  case 101:
423  ret = SwitchingProtocol;
424  break;
425  case 102:
426  ret = Processing;
427  break;
428  case 103:
429  ret = EarlyHints;
430  break;
431 
432  case 200:
433  ret = Ok;
434  break;
435  case 201:
436  ret = Created;
437  break;
438  case 202:
439  ret = Accepted;
440  break;
441  case 203:
443  break;
444  case 204:
445  ret = NoContent;
446  break;
447  case 205:
448  ret = ResetContent;
449  break;
450  case 206:
451  ret = PartialContent;
452  break;
453  case 207:
454  ret = MultiStatus;
455  break;
456  case 208:
457  ret = AlreadyReported;
458  break;
459  case 226:
460  ret = ImUsed;
461  break;
462 
463  case 300:
464  ret = MultipleChoice;
465  break;
466  case 301:
467  ret = MovedPermanently;
468  break;
469  case 302:
470  ret = Found;
471  break;
472  case 303:
473  ret = SeeOther;
474  break;
475  case 304:
476  ret = NotModified;
477  break;
478  case 305:
479  ret = UseProxy;
480  break;
481  case 307:
482  ret = TemporaryRedirect;
483  break;
484  case 308:
485  ret = PermanentRedirect;
486  break;
487 
488  case 400:
489  ret = BadRequest;
490  break;
491  case 401:
492  ret = Unauthorized;
493  break;
494  case 402:
495  ret = PaymentRequired;
496  break;
497  case 403:
498  ret = Forbidden;
499  break;
500  case 404:
501  ret = NotFound;
502  break;
503  case 405:
504  ret = MethodNotAllowed;
505  break;
506  case 406:
507  ret = NotAcceptable;
508  break;
509  case 407:
511  break;
512  case 408:
513  ret = RequestTimeout;
514  break;
515  case 409:
516  ret = Conflict;
517  break;
518  case 410:
519  ret = Gone;
520  break;
521  case 411:
522  ret = LengthRequired;
523  break;
524  case 412:
525  ret = PreconditionFailed;
526  break;
527  case 413:
528  ret = PayloadTooLarge;
529  break;
530  case 414:
531  ret = UriTooLong;
532  break;
533  case 415:
534  ret = UnsupportedMediaType;
535  break;
536  case 416:
537  ret = RangeNotSatisfiable;
538  break;
539  case 417:
540  ret = ExpectationFailed;
541  break;
542  case 418:
543  ret = ImaTeapot;
544  break;
545  case 421:
546  ret = MisdirectedRequest;
547  break;
548  case 422:
549  ret = UnprocessableEntity;
550  break;
551  case 423:
552  ret = Locked;
553  break;
554  case 424:
555  ret = FailedDependency;
556  break;
557  case 425:
558  ret = TooEarly;
559  break;
560  case 426:
561  ret = UpgradeRequired;
562  break;
563  case 428:
564  ret = PreconditionRequired;
565  break;
566  case 429:
567  ret = TooManyRequests;
568  break;
569  case 431:
571  break;
572  case 451:
574  break;
575 
576  case 500:
577  ret = InternalServerError;
578  break;
579  case 501:
580  ret = NotImplemented;
581  break;
582  case 502:
583  ret = BadGateway;
584  break;
585  case 503:
586  ret = ServiceUnavailable;
587  break;
588  case 504:
589  ret = GatewayTimeout;
590  break;
591  case 505:
593  break;
594  case 506:
595  ret = VariantAlsoNegotiates;
596  break;
597  case 507:
598  ret = InsufficientStorage;
599  break;
600  case 508:
601  ret = LoopDetected;
602  break;
603  case 510:
604  ret = NotExtended;
605  break;
606  case 511:
608  break;
609  default:
610  NS_FATAL_ERROR ("Unknown status: " << m_status);
611  break;
612  }
613  return ret;
614 }
615 
616 void
618 
619  NS_LOG_FUNCTION (this << static_cast<uint16_t> (m_method));
620 
621  switch (method)
622  {
623  case DELETE:
624  m_method = 0;
625  break;
626  case GET:
627  m_method = 1;
628  break;
629  case HEAD:
630  m_method = 2;
631  break;
632  case PATCH:
633  m_method = 3;
634  break;
635  case POST:
636  m_method = 4;
637  break;
638  case PUT:
639  m_method = 5;
640  break;
641  default:
642  NS_FATAL_ERROR ("Unknown Content-Type: " << m_method);
643  break;
644  }
645 
646 }
647 
650 {
651 
652  HttpMethod ret;
653  switch (m_method)
654  {
655  case 0:
656  ret = DELETE;
657  break;
658  case 1:
659  ret = GET;
660  break;
661  case 2:
662  ret = HEAD;
663  break;
664  case 3:
665  ret = PATCH;
666  break;
667  case 4:
668  ret = POST;
669  break;
670  case 5:
671  ret = PUT;
672  break;
673  NS_FATAL_ERROR ("Unknown Method: " << m_method);
674  break;
675  }
676  return ret;
677 
678 }
679 
680 std::string
682 {
683  return m_uri;
684 }
685 
686 void
687 HttpHeader::SetUri(std::string uri)
688 {
689  NS_LOG_FUNCTION (this << uri << m_uri.length() );
690  m_uri = uri;
691  SetContentLength(m_uri.length());
692 }
693 
694 } // namespace ns3
iterator in a Buffer instance
Definition: buffer.h:100
uint64_t ReadU64()
Definition: buffer.cc:984
void Read(uint8_t *buffer, uint32_t size)
Definition: buffer.cc:1125
uint32_t ReadU32()
Definition: buffer.cc:966
uint32_t GetDistanceFrom(const Iterator &o) const
Definition: buffer.cc:780
uint16_t ReadU16()
Definition: buffer.h:1035
Protocol header serialization and deserialization.
Definition: header.h:44
virtual uint32_t Deserialize(Buffer::Iterator start)=0
Deserialize the object from a buffer iterator.
uint16_t m_method
" Connection method field in integer format.
Definition: http-header.h:232
std::string m_uri
Definition: http-header.h:237
virtual void Serialize(Buffer::Iterator start) const
Definition: http-header.cc:69
HttpHeader()
Creates an empty instance .
Definition: http-header.cc:33
uint16_t m_contentType
" Content type field in integer format.
Definition: http-header.h:234
virtual void Print(std::ostream &os) const
Definition: http-header.cc:121
HttpStatus GetStatus() const
Definition: http-header.cc:414
virtual TypeId GetInstanceTypeId() const
Get the most derived TypeId for this Object.
Definition: http-header.cc:54
virtual uint32_t GetSerializedSize() const
Definition: http-header.cc:60
uint64_t GetSize(void) const
Get the size information that the header is carrying.
Definition: http-header.cc:205
std::string GetUri() const
Definition: http-header.cc:681
static TypeId GetTypeId()
Returns the object TypeId.
Definition: http-header.cc:44
ContentType_t GetContentType() const
Definition: http-header.cc:162
void SetSize(uint64_t size)
Set the size information that the header will carry.
Definition: http-header.cc:199
void SetContentType(ContentType_t contentType)
Definition: http-header.cc:141
void SetContentLength(uint32_t contentLength)
Definition: http-header.cc:184
void SetStatus(HttpStatus status)
Definition: http-header.cc:211
uint16_t m_status
" Connection status field in integer format.
Definition: http-header.h:233
@ NetworkAuthenticationRequired
Definition: http-header.h:166
@ ProxyAuthenticationRequired
Definition: http-header.h:133
@ RequestHeaderFieldsTooLarge
Definition: http-header.h:153
@ NonAuthoritativeInformation
Definition: http-header.h:109
@ UnavailableForLegalReasons
Definition: http-header.h:154
HttpMethod GetMethod() const
Definition: http-header.cc:649
@ HEAD
Http Method Head.
Definition: http-header.h:93
@ DELETE
Http Method Delete.
Definition: http-header.h:91
@ PUT
Http Method Put.
Definition: http-header.h:96
@ GET
Http Method GET.
Definition: http-header.h:92
@ PATCH
Http Method Patch.
Definition: http-header.h:94
@ POST
Http Method Post.
Definition: http-header.h:95
uint32_t m_contentLength
" Content length field (in bytes unit).
Definition: http-header.h:235
uint32_t GetContentLength() const
Definition: http-header.cc:192
void SetUri(std::string uri)
Definition: http-header.cc:687
ContentType_t
The possible types of content (default = NOT_SET).
Definition: http-header.h:84
@ NOT_SET
Integer equivalent = 0.
Definition: http-header.h:85
@ MAIN_OBJECT
Integer equivalent = 1.
Definition: http-header.h:86
@ EMBEDDED_OBJECT
Integer equivalent = 2.
Definition: http-header.h:87
std::string ToString() const
Definition: http-header.cc:132
void SetMethod(HttpMethod method)
Definition: http-header.cc:617
uint64_t m_size
The 'size' information that the header is carrying.
Definition: http-header.h:236
a unique identifier for an interface.
Definition: type-id.h:59
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition: type-id.cc:931
#define NS_ASSERT(condition)
At runtime, in debugging builds, if this condition is not true, the program prints the source file,...
Definition: assert.h:66
#define NS_FATAL_ERROR(msg)
Report a fatal error with a message and terminate.
Definition: fatal-error.h:179
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:202
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition: object-base.h:46
Every class exported by the ns3 library is enclosed in the ns3 namespace.