puma 2.2.0 → 8.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (136) hide show
  1. checksums.yaml +7 -0
  2. data/History.md +3334 -0
  3. data/LICENSE +23 -20
  4. data/README.md +387 -100
  5. data/bin/puma-wild +25 -0
  6. data/bin/pumactl +1 -1
  7. data/docs/5.0-Upgrade.md +98 -0
  8. data/docs/6.0-Upgrade.md +56 -0
  9. data/docs/7.0-Upgrade.md +52 -0
  10. data/docs/8.0-Upgrade.md +100 -0
  11. data/docs/architecture.md +74 -0
  12. data/docs/compile_options.md +55 -0
  13. data/docs/deployment.md +137 -0
  14. data/docs/fork_worker.md +41 -0
  15. data/docs/grpc.md +62 -0
  16. data/docs/images/favicon.svg +1 -0
  17. data/docs/images/puma-connection-flow-no-reactor.png +0 -0
  18. data/docs/images/puma-connection-flow.png +0 -0
  19. data/docs/images/puma-general-arch.png +0 -0
  20. data/docs/images/running-puma.svg +1 -0
  21. data/docs/images/standard-logo.svg +1 -0
  22. data/docs/java_options.md +54 -0
  23. data/docs/jungle/README.md +9 -0
  24. data/docs/jungle/rc.d/README.md +74 -0
  25. data/docs/jungle/rc.d/puma +61 -0
  26. data/docs/jungle/rc.d/puma.conf +10 -0
  27. data/docs/kubernetes.md +73 -0
  28. data/docs/nginx.md +5 -5
  29. data/docs/plugins.md +42 -0
  30. data/docs/rails_dev_mode.md +28 -0
  31. data/docs/restart.md +65 -0
  32. data/docs/signals.md +98 -0
  33. data/docs/stats.md +148 -0
  34. data/docs/systemd.md +253 -0
  35. data/docs/testing_benchmarks_local_files.md +150 -0
  36. data/docs/testing_test_rackup_ci_files.md +36 -0
  37. data/ext/puma_http11/PumaHttp11Service.java +2 -2
  38. data/ext/puma_http11/extconf.rb +59 -2
  39. data/ext/puma_http11/http11_parser.c +319 -487
  40. data/ext/puma_http11/http11_parser.h +15 -13
  41. data/ext/puma_http11/http11_parser.java.rl +64 -94
  42. data/ext/puma_http11/http11_parser.rl +27 -24
  43. data/ext/puma_http11/http11_parser_common.rl +8 -8
  44. data/ext/puma_http11/mini_ssl.c +696 -38
  45. data/ext/puma_http11/no_ssl/PumaHttp11Service.java +15 -0
  46. data/ext/puma_http11/org/jruby/puma/EnvKey.java +241 -0
  47. data/ext/puma_http11/org/jruby/puma/Http11.java +241 -145
  48. data/ext/puma_http11/org/jruby/puma/Http11Parser.java +174 -221
  49. data/ext/puma_http11/org/jruby/puma/MiniSSL.java +413 -193
  50. data/ext/puma_http11/puma_http11.c +183 -175
  51. data/lib/puma/app/status.rb +77 -29
  52. data/lib/puma/binder.rb +349 -119
  53. data/lib/puma/cli.rb +163 -801
  54. data/lib/puma/client.rb +627 -144
  55. data/lib/puma/client_env.rb +171 -0
  56. data/lib/puma/cluster/worker.rb +183 -0
  57. data/lib/puma/cluster/worker_handle.rb +127 -0
  58. data/lib/puma/cluster.rb +634 -0
  59. data/lib/puma/cluster_accept_loop_delay.rb +91 -0
  60. data/lib/puma/commonlogger.rb +115 -0
  61. data/lib/puma/configuration.rb +420 -198
  62. data/lib/puma/const.rb +266 -115
  63. data/lib/puma/control_cli.rb +219 -120
  64. data/lib/puma/detect.rb +56 -2
  65. data/lib/puma/dsl.rb +1562 -0
  66. data/lib/puma/error_logger.rb +115 -0
  67. data/lib/puma/events.rb +44 -60
  68. data/lib/puma/io_buffer.rb +48 -5
  69. data/lib/puma/jruby_restart.rb +2 -51
  70. data/lib/puma/json_serialization.rb +96 -0
  71. data/lib/puma/launcher/bundle_pruner.rb +102 -0
  72. data/lib/puma/launcher.rb +501 -0
  73. data/lib/puma/log_writer.rb +153 -0
  74. data/lib/puma/minissl/context_builder.rb +96 -0
  75. data/lib/puma/minissl.rb +355 -37
  76. data/lib/puma/null_io.rb +79 -12
  77. data/lib/puma/plugin/systemd.rb +90 -0
  78. data/lib/puma/plugin/tmp_restart.rb +36 -0
  79. data/lib/puma/plugin.rb +111 -0
  80. data/lib/puma/rack/builder.rb +297 -0
  81. data/lib/puma/rack/urlmap.rb +93 -0
  82. data/lib/puma/rack_default.rb +21 -4
  83. data/lib/puma/reactor.rb +102 -133
  84. data/lib/puma/response.rb +532 -0
  85. data/lib/puma/runner.rb +211 -0
  86. data/lib/puma/sd_notify.rb +146 -0
  87. data/lib/puma/server.rb +582 -445
  88. data/lib/puma/server_plugin_control.rb +32 -0
  89. data/lib/puma/single.rb +72 -0
  90. data/lib/puma/state_file.rb +69 -0
  91. data/lib/puma/thread_pool.rb +389 -57
  92. data/lib/puma/util.rb +125 -0
  93. data/lib/puma.rb +80 -6
  94. data/lib/rack/handler/puma.rb +125 -47
  95. data/tools/Dockerfile +26 -0
  96. data/tools/trickletest.rb +44 -0
  97. metadata +88 -148
  98. data/COPYING +0 -55
  99. data/Gemfile +0 -10
  100. data/History.txt +0 -302
  101. data/Manifest.txt +0 -60
  102. data/Rakefile +0 -165
  103. data/TODO +0 -5
  104. data/docs/config.md +0 -0
  105. data/ext/puma_http11/ext_help.h +0 -15
  106. data/ext/puma_http11/io_buffer.c +0 -154
  107. data/lib/puma/accept_nonblock.rb +0 -23
  108. data/lib/puma/capistrano.rb +0 -34
  109. data/lib/puma/compat.rb +0 -11
  110. data/lib/puma/daemon_ext.rb +0 -20
  111. data/lib/puma/delegation.rb +0 -11
  112. data/lib/puma/java_io_buffer.rb +0 -45
  113. data/lib/puma/rack_patch.rb +0 -25
  114. data/puma.gemspec +0 -45
  115. data/test/test_app_status.rb +0 -88
  116. data/test/test_cli.rb +0 -171
  117. data/test/test_config.rb +0 -16
  118. data/test/test_http10.rb +0 -27
  119. data/test/test_http11.rb +0 -126
  120. data/test/test_integration.rb +0 -154
  121. data/test/test_iobuffer.rb +0 -38
  122. data/test/test_minissl.rb +0 -25
  123. data/test/test_null_io.rb +0 -31
  124. data/test/test_persistent.rb +0 -238
  125. data/test/test_puma_server.rb +0 -224
  126. data/test/test_rack_handler.rb +0 -10
  127. data/test/test_rack_server.rb +0 -141
  128. data/test/test_thread_pool.rb +0 -146
  129. data/test/test_unix_socket.rb +0 -39
  130. data/test/test_ws.rb +0 -89
  131. data/tools/jungle/init.d/README.md +0 -54
  132. data/tools/jungle/init.d/puma +0 -332
  133. data/tools/jungle/init.d/run-puma +0 -3
  134. data/tools/jungle/upstart/README.md +0 -61
  135. data/tools/jungle/upstart/puma-manager.conf +0 -31
  136. data/tools/jungle/upstart/puma.conf +0 -52
@@ -1,11 +1,13 @@
1
1
  /**
2
2
  * Copyright (c) 2005 Zed A. Shaw
3
3
  * You can redistribute it and/or modify it under the same terms as Ruby.
4
+ * License 3-clause BSD
4
5
  */
5
6
 
6
7
  #ifndef http11_parser_h
7
8
  #define http11_parser_h
8
9
 
10
+ #define RSTRING_NOT_MODIFIED 1
9
11
  #include "ruby.h"
10
12
 
11
13
  #include <sys/types.h>
@@ -16,19 +18,19 @@
16
18
 
17
19
  #define BUFFER_LEN 1024
18
20
 
19
- struct http_parser;
21
+ struct puma_parser;
20
22
 
21
- typedef void (*element_cb)(struct http_parser* hp,
23
+ typedef void (*element_cb)(struct puma_parser* hp,
22
24
  const char *at, size_t length);
23
25
 
24
- typedef void (*field_cb)(struct http_parser* hp,
26
+ typedef void (*field_cb)(struct puma_parser* hp,
25
27
  const char *field, size_t flen,
26
28
  const char *value, size_t vlen);
27
29
 
28
- typedef struct http_parser {
30
+ typedef struct puma_parser {
29
31
  int cs;
30
- size_t body_start;
31
32
  int content_len;
33
+ size_t body_start;
32
34
  size_t nread;
33
35
  size_t mark;
34
36
  size_t field_start;
@@ -44,20 +46,20 @@ typedef struct http_parser {
44
46
  element_cb fragment;
45
47
  element_cb request_path;
46
48
  element_cb query_string;
47
- element_cb http_version;
49
+ element_cb server_protocol;
48
50
  element_cb header_done;
49
51
 
50
52
  char buf[BUFFER_LEN];
51
53
 
52
- } http_parser;
54
+ } puma_parser;
53
55
 
54
- int http_parser_init(http_parser *parser);
55
- int http_parser_finish(http_parser *parser);
56
- size_t http_parser_execute(http_parser *parser, const char *data,
56
+ int puma_parser_init(puma_parser *parser);
57
+ int puma_parser_finish(puma_parser *parser);
58
+ size_t puma_parser_execute(puma_parser *parser, const char *data,
57
59
  size_t len, size_t off);
58
- int http_parser_has_error(http_parser *parser);
59
- int http_parser_is_finished(http_parser *parser);
60
+ int puma_parser_has_error(puma_parser *parser);
61
+ int puma_parser_is_finished(puma_parser *parser);
60
62
 
61
- #define http_parser_nread(parser) (parser)->nread
63
+ #define puma_parser_nread(parser) (parser)->nread
62
64
 
63
65
  #endif
@@ -1,5 +1,8 @@
1
1
  package org.jruby.puma;
2
2
 
3
+ import org.jruby.Ruby;
4
+ import org.jruby.RubyHash;
5
+ import org.jruby.RubyString;
3
6
  import org.jruby.util.ByteList;
4
7
 
5
8
  public class Http11Parser {
@@ -7,138 +10,105 @@ public class Http11Parser {
7
10
  /** Machine **/
8
11
 
9
12
  %%{
10
-
11
- machine http_parser;
12
13
 
13
- action mark {parser.mark = fpc; }
14
+ machine puma_parser;
15
+
16
+ action mark {this.mark = fpc; }
14
17
 
15
- action start_field { parser.field_start = fpc; }
16
- action snake_upcase_field { /* FIXME stub */ }
18
+ action start_field { this.field_start = fpc; }
19
+ action snake_upcase_field { /* done lazily as needed */ }
17
20
  action write_field {
18
- parser.field_len = fpc-parser.field_start;
21
+ this.field_len = fpc-this.field_start;
19
22
  }
20
23
 
21
- action start_value { parser.mark = fpc; }
22
- action write_value {
23
- if(parser.http_field != null) {
24
- parser.http_field.call(parser.data, parser.field_start, parser.field_len, parser.mark, fpc-parser.mark);
25
- }
24
+ action start_value { this.mark = fpc; }
25
+ action write_value {
26
+ Http11.http_field(runtime, envStrings, this, fpc-this.mark);
26
27
  }
27
- action request_method {
28
- if(parser.request_method != null)
29
- parser.request_method.call(parser.data, parser.mark, fpc-parser.mark);
28
+ action request_method {
29
+ Http11.request_method(runtime, envStrings, this, fpc-this.mark);
30
30
  }
31
- action request_uri {
32
- if(parser.request_uri != null)
33
- parser.request_uri.call(parser.data, parser.mark, fpc-parser.mark);
31
+ action request_uri {
32
+ Http11.request_uri(runtime, envStrings, this, fpc-this.mark);
34
33
  }
35
- action fragment {
36
- if(parser.fragment != null)
37
- parser.fragment.call(parser.data, parser.mark, fpc-parser.mark);
34
+ action fragment {
35
+ Http11.fragment(runtime, envStrings, this, fpc-this.mark);
38
36
  }
39
37
 
40
- action start_query {parser.query_start = fpc; }
41
- action query_string {
42
- if(parser.query_string != null)
43
- parser.query_string.call(parser.data, parser.query_start, fpc-parser.query_start);
38
+ action start_query {this.query_start = fpc; }
39
+ action query_string {
40
+ Http11.query_string(runtime, envStrings, this, fpc-this.query_start);
44
41
  }
45
42
 
46
- action http_version {
47
- if(parser.http_version != null)
48
- parser.http_version.call(parser.data, parser.mark, fpc-parser.mark);
43
+ action server_protocol {
44
+ Http11.server_protocol(runtime, envStrings, this, fpc-this.mark);
49
45
  }
50
46
 
51
47
  action request_path {
52
- if(parser.request_path != null)
53
- parser.request_path.call(parser.data, parser.mark, fpc-parser.mark);
48
+ Http11.request_path(runtime, envStrings, this, fpc-this.mark);
54
49
  }
55
50
 
56
51
  action done {
57
- parser.body_start = fpc + 1;
58
- if(parser.header_done != null)
59
- parser.header_done.call(parser.data, fpc + 1, pe - fpc - 1);
52
+ this.body_start = fpc + 1;
53
+ http.header_done(runtime, this, fpc + 1, pe - fpc - 1);
60
54
  fbreak;
61
55
  }
62
56
 
63
- include http_parser_common "http11_parser_common.rl";
57
+ include puma_parser_common "http11_parser_common.rl";
64
58
 
65
59
  }%%
66
60
 
67
61
  /** Data **/
68
- %% write data;
62
+ %% write data noentry;
69
63
 
70
- public static interface ElementCB {
71
- public void call(Object data, int at, int length);
72
- }
64
+ int cs;
65
+ int body_start;
66
+ int nread;
67
+ int mark;
68
+ int field_start;
69
+ int field_len;
70
+ int query_start;
73
71
 
74
- public static interface FieldCB {
75
- public void call(Object data, int field, int flen, int value, int vlen);
76
- }
72
+ RubyHash data;
73
+ byte[] buffer;
77
74
 
78
- public static class HttpParser {
79
- int cs;
80
- int body_start;
81
- int content_len;
82
- int nread;
83
- int mark;
84
- int field_start;
85
- int field_len;
86
- int query_start;
87
-
88
- Object data;
89
- ByteList buffer;
90
-
91
- public FieldCB http_field;
92
- public ElementCB request_method;
93
- public ElementCB request_uri;
94
- public ElementCB fragment;
95
- public ElementCB request_path;
96
- public ElementCB query_string;
97
- public ElementCB http_version;
98
- public ElementCB header_done;
99
-
100
- public void init() {
101
- cs = 0;
102
-
103
- %% write init;
104
-
105
- body_start = 0;
106
- content_len = 0;
107
- mark = 0;
108
- nread = 0;
109
- field_len = 0;
110
- field_start = 0;
111
- }
112
- }
75
+ public void init() {
113
76
 
114
- public final HttpParser parser = new HttpParser();
77
+ %% write init;
78
+
79
+ body_start = 0;
80
+ mark = 0;
81
+ nread = 0;
82
+ field_len = 0;
83
+ field_start = 0;
84
+ }
115
85
 
116
- public int execute(ByteList buffer, int off) {
86
+ public int execute(Ruby runtime, Http11 http, ByteList buffer, int off) {
117
87
  int p, pe;
118
- int cs = parser.cs;
88
+ int cs = this.cs;
119
89
  int len = buffer.length();
90
+ int beg = buffer.begin();
91
+ RubyString[] envStrings = http.envStrings;
120
92
  assert off<=len : "offset past end of buffer";
121
93
 
122
- p = off;
123
- pe = len;
124
- // get a copy of the bytes, since it may not start at 0
125
- // FIXME: figure out how to just use the bytes in-place
126
- byte[] data = buffer.bytes();
127
- parser.buffer = buffer;
94
+ p = beg + off;
95
+ pe = beg + len;
96
+ byte[] data = buffer.unsafeBytes();
97
+ this.buffer = data;
128
98
 
129
99
  %% write exec;
130
100
 
131
- parser.cs = cs;
132
- parser.nread += (p - off);
101
+ this.cs = cs;
102
+ this.nread += (p - off);
133
103
 
134
104
  assert p <= pe : "buffer overflow after parsing execute";
135
- assert parser.nread <= len : "nread longer than length";
136
- assert parser.body_start <= len : "body starts after buffer end";
137
- assert parser.mark < len : "mark is after buffer end";
138
- assert parser.field_len <= len : "field has length longer than whole buffer";
139
- assert parser.field_start < len : "field starts after buffer end";
105
+ assert this.nread <= len : "nread longer than length";
106
+ assert this.body_start <= len : "body starts after buffer end";
107
+ assert this.mark < len : "mark is after buffer end";
108
+ assert this.field_len <= len : "field has length longer than whole buffer";
109
+ assert this.field_start < len : "field starts after buffer end";
140
110
 
141
- return parser.nread;
111
+ return this.nread;
142
112
  }
143
113
 
144
114
  public int finish() {
@@ -152,10 +122,10 @@ public class Http11Parser {
152
122
  }
153
123
 
154
124
  public boolean has_error() {
155
- return parser.cs == http_parser_error;
125
+ return this.cs == puma_parser_error;
156
126
  }
157
127
 
158
128
  public boolean is_finished() {
159
- return parser.cs == http_parser_first_final;
129
+ return this.cs == puma_parser_first_final;
160
130
  }
161
131
  }
@@ -1,6 +1,7 @@
1
1
  /**
2
2
  * Copyright (c) 2005 Zed A. Shaw
3
3
  * You can redistribute it and/or modify it under the same terms as Ruby.
4
+ * License 3-clause BSD
4
5
  */
5
6
  #include "http11_parser.h"
6
7
  #include <stdio.h>
@@ -11,12 +12,14 @@
11
12
 
12
13
  /*
13
14
  * capitalizes all lower-case ASCII characters,
14
- * converts dashes to underscores.
15
+ * converts dashes to underscores, and underscores to commas.
15
16
  */
16
17
  static void snake_upcase_char(char *c)
17
18
  {
18
19
  if (*c >= 'a' && *c <= 'z')
19
20
  *c &= ~0x20;
21
+ else if (*c == '_')
22
+ *c = ',';
20
23
  else if (*c == '-')
21
24
  *c = '_';
22
25
  }
@@ -28,15 +31,15 @@ static void snake_upcase_char(char *c)
28
31
  /** Machine **/
29
32
 
30
33
  %%{
31
-
32
- machine http_parser;
34
+
35
+ machine puma_parser;
33
36
 
34
37
  action mark { MARK(mark, fpc); }
35
38
 
36
39
 
37
40
  action start_field { MARK(field_start, fpc); }
38
41
  action snake_upcase_field { snake_upcase_char((char *)fpc); }
39
- action write_field {
42
+ action write_field {
40
43
  parser->field_len = LEN(field_start, fpc);
41
44
  }
42
45
 
@@ -44,10 +47,10 @@ static void snake_upcase_char(char *c)
44
47
  action write_value {
45
48
  parser->http_field(parser, PTR_TO(field_start), parser->field_len, PTR_TO(mark), LEN(mark, fpc));
46
49
  }
47
- action request_method {
50
+ action request_method {
48
51
  parser->request_method(parser, PTR_TO(mark), LEN(mark, fpc));
49
52
  }
50
- action request_uri {
53
+ action request_uri {
51
54
  parser->request_uri(parser, PTR_TO(mark), LEN(mark, fpc));
52
55
  }
53
56
  action fragment {
@@ -55,32 +58,32 @@ static void snake_upcase_char(char *c)
55
58
  }
56
59
 
57
60
  action start_query { MARK(query_start, fpc); }
58
- action query_string {
61
+ action query_string {
59
62
  parser->query_string(parser, PTR_TO(query_start), LEN(query_start, fpc));
60
63
  }
61
64
 
62
- action http_version {
63
- parser->http_version(parser, PTR_TO(mark), LEN(mark, fpc));
65
+ action server_protocol {
66
+ parser->server_protocol(parser, PTR_TO(mark), LEN(mark, fpc));
64
67
  }
65
68
 
66
69
  action request_path {
67
70
  parser->request_path(parser, PTR_TO(mark), LEN(mark,fpc));
68
71
  }
69
72
 
70
- action done {
71
- parser->body_start = fpc - buffer + 1;
73
+ action done {
74
+ parser->body_start = fpc - buffer + 1;
72
75
  parser->header_done(parser, fpc + 1, pe - fpc - 1);
73
76
  fbreak;
74
77
  }
75
78
 
76
- include http_parser_common "http11_parser_common.rl";
79
+ include puma_parser_common "http11_parser_common.rl";
77
80
 
78
81
  }%%
79
82
 
80
83
  /** Data **/
81
- %% write data;
84
+ %% write data noentry;
82
85
 
83
- int http_parser_init(http_parser *parser) {
86
+ int puma_parser_init(puma_parser *parser) {
84
87
  int cs = 0;
85
88
  %% write init;
86
89
  parser->cs = cs;
@@ -98,7 +101,7 @@ int http_parser_init(http_parser *parser) {
98
101
 
99
102
 
100
103
  /** exec **/
101
- size_t http_parser_execute(http_parser *parser, const char *buffer, size_t len, size_t off) {
104
+ size_t puma_parser_execute(puma_parser *parser, const char *buffer, size_t len, size_t off) {
102
105
  const char *p, *pe;
103
106
  int cs = parser->cs;
104
107
 
@@ -108,11 +111,11 @@ size_t http_parser_execute(http_parser *parser, const char *buffer, size_t len,
108
111
  pe = buffer+len;
109
112
 
110
113
  /* assert(*pe == '\0' && "pointer does not end on NUL"); */
111
- assert(pe - p == len - off && "pointers aren't same distance");
114
+ assert((size_t) (pe - p) == len - off && "pointers aren't same distance");
112
115
 
113
116
  %% write exec;
114
117
 
115
- if (!http_parser_has_error(parser))
118
+ if (!puma_parser_has_error(parser))
116
119
  parser->cs = cs;
117
120
  parser->nread += p - (buffer + off);
118
121
 
@@ -126,21 +129,21 @@ size_t http_parser_execute(http_parser *parser, const char *buffer, size_t len,
126
129
  return(parser->nread);
127
130
  }
128
131
 
129
- int http_parser_finish(http_parser *parser)
132
+ int puma_parser_finish(puma_parser *parser)
130
133
  {
131
- if (http_parser_has_error(parser) ) {
134
+ if (puma_parser_has_error(parser) ) {
132
135
  return -1;
133
- } else if (http_parser_is_finished(parser) ) {
136
+ } else if (puma_parser_is_finished(parser) ) {
134
137
  return 1;
135
138
  } else {
136
139
  return 0;
137
140
  }
138
141
  }
139
142
 
140
- int http_parser_has_error(http_parser *parser) {
141
- return parser->cs == http_parser_error;
143
+ int puma_parser_has_error(puma_parser *parser) {
144
+ return parser->cs == puma_parser_error;
142
145
  }
143
146
 
144
- int http_parser_is_finished(http_parser *parser) {
145
- return parser->cs >= http_parser_first_final;
147
+ int puma_parser_is_finished(puma_parser *parser) {
148
+ return parser->cs >= puma_parser_first_final;
146
149
  }
@@ -1,6 +1,6 @@
1
1
  %%{
2
-
3
- machine http_parser_common;
2
+
3
+ machine puma_parser_common;
4
4
 
5
5
  #### HTTP PROTOCOL GRAMMAR
6
6
  # line endings
@@ -15,8 +15,8 @@
15
15
  national = any -- (alpha | digit | reserved | extra | safe | unsafe);
16
16
  unreserved = (alpha | digit | safe | extra | national);
17
17
  escape = ("%" xdigit xdigit);
18
- uchar = (unreserved | escape);
19
- pchar = (uchar | ":" | "@" | "&" | "=" | "+");
18
+ uchar = (unreserved | escape | "%");
19
+ pchar = (uchar | ":" | "@" | "&" | "=" | "+" | ";");
20
20
  tspecials = ("(" | ")" | "<" | ">" | "@" | "," | ";" | ":" | "\\" | "\"" | "/" | "[" | "]" | "?" | "=" | "{" | "}" | " " | "\t");
21
21
 
22
22
  # elements
@@ -30,7 +30,7 @@
30
30
  query = ( uchar | reserved )* %query_string ;
31
31
  param = ( pchar | "/" )* ;
32
32
  params = ( param ( ";" param )* ) ;
33
- rel_path = ( path? %request_path (";" params)? ) ("?" %start_query query)?;
33
+ rel_path = ( path? %request_path ) ("?" %start_query query)?;
34
34
  absolute_path = ( "/"+ rel_path );
35
35
 
36
36
  Request_URI = ( "*" | absolute_uri | absolute_path ) >mark %request_uri;
@@ -38,12 +38,12 @@
38
38
  Method = ( upper | digit | safe ){1,20} >mark %request_method;
39
39
 
40
40
  http_number = ( digit+ "." digit+ ) ;
41
- HTTP_Version = ( "HTTP/" http_number ) >mark %http_version ;
42
- Request_Line = ( Method " " Request_URI ("#" Fragment){0,1} " " HTTP_Version CRLF ) ;
41
+ Server_Protocol = ( "HTTP/" http_number ) >mark %server_protocol ;
42
+ Request_Line = ( Method " " Request_URI ("#" Fragment){0,1} " " Server_Protocol CRLF ) ;
43
43
 
44
44
  field_name = ( token -- ":" )+ >start_field $snake_upcase_field %write_field;
45
45
 
46
- field_value = any* >start_value %write_value;
46
+ field_value = ( (any -- CTL) | "\t" )* >start_value %write_value;
47
47
 
48
48
  message_header = field_name ":" " "* field_value :> CRLF;
49
49