OpenVAS Scanner  7.0.1~git
nasl_http.c
Go to the documentation of this file.
1 /* Based on work Copyright (C) 2002 - 2004 Tenable Network Security
2  *
3  * SPDX-License-Identifier: GPL-2.0-only
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License
7  * version 2 as 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., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
17  */
18 
19 #include "nasl_http.h"
20 
21 #include "../misc/plugutils.h" /* plug_get_host_fqdn */
22 #include "../misc/vendorversion.h" /* for vendor_version_get */
23 #include "exec.h"
24 #include "nasl_debug.h"
25 #include "nasl_func.h"
26 #include "nasl_global_ctxt.h"
27 #include "nasl_lex_ctxt.h"
28 #include "nasl_socket.h"
29 #include "nasl_tree.h"
30 #include "nasl_var.h"
31 
32 #include <ctype.h> /* for isspace */
33 #include <glib.h>
34 #include <gvm/base/prefs.h> /* for prefs_get */
35 #include <gvm/util/kb.h> /* for kb_item_get_str */
36 #include <string.h> /* for strlen */
37 
38 #undef G_LOG_DOMAIN
39 
42 #define G_LOG_DOMAIN "lib nasl"
43 
44 /*-----------------[ http_* functions ]-------------------------------*/
45 
46 tree_cell *
48 {
49  return nasl_open_sock_tcp_bufsz (lexic, 65536);
50 }
51 
52 tree_cell *
54 {
55  return nasl_close_socket (lexic);
56 }
57 
58 static char *
59 build_encode_URL (char *method, char *path, char *name, char *httpver)
60 {
61  char *ret, *ret2;
62 
63  if (path == NULL)
64  ret = g_strdup (name);
65  else
66  ret = g_strdup_printf ("%s/%s", path, name);
67 
68  g_debug ("Request => %s", ret);
69  ret2 = g_strdup_printf ("%s %s %s", method, ret, httpver);
70  g_free (ret);
71  return ret2;
72 }
73 
74 static tree_cell *
75 _http_req (lex_ctxt *lexic, char *keyword)
76 {
77  tree_cell *retc;
78  char *request, *auth, tmp[32];
79  char *item = get_str_var_by_name (lexic, "item");
80  char *data = get_str_var_by_name (lexic, "data");
81  int port = get_int_var_by_name (lexic, "port", -1);
82  struct script_infos *script_infos = lexic->script_infos;
83  int ver;
84  kb_t kb;
85 
86  if (item == NULL || port < 0)
87  {
88  nasl_perror (lexic,
89  "Error : http_* functions have the following syntax :\n");
90  nasl_perror (lexic, "http_*(port:<port>, item:<item> [, data:<data>]\n");
91  return NULL;
92  }
93 
94  if (port <= 0 || port > 65535)
95  {
96  nasl_perror (lexic, "http_req: invalid value %d for port parameter\n",
97  port);
98  return NULL;
99  }
100 
101  kb = plug_get_kb (script_infos);
102  g_snprintf (tmp, sizeof (tmp), "/tmp/http/auth/%d", port);
103  auth = kb_item_get_str (kb, tmp);
104 
105  if (!auth)
106  auth = kb_item_get_str (kb, "http/auth");
107 
108  g_snprintf (tmp, sizeof (tmp), "http/%d", port);
109  ver = kb_item_get_int (kb, tmp);
110 
111  if ((ver <= 0) || (ver == 11))
112  {
113  char *hostname, *ua, *hostheader, *url;
114 
116  if (hostname == NULL)
117  return NULL;
118  /* global_settings.nasl */
119  ua = get_plugin_preference ("1.3.6.1.4.1.25623.1.0.12288",
120  "HTTP User-Agent", -1);
121  if (!ua || strlen (g_strstrip (ua)) == 0)
122  {
123  g_free (ua);
124  if (!vendor_version_get () || *vendor_version_get () == '\0')
125  ua = g_strdup_printf ("Mozilla/5.0 [en] (X11, U; OpenVAS-VT %s)",
126  OPENVAS_NASL_VERSION);
127  else
128  ua = g_strdup_printf ("Mozilla/5.0 [en] (X11, U; %s)",
129  vendor_version_get ());
130  }
131 
132  /* Servers should not have a problem with port 80 or 443 appended.
133  * RFC2616 allows to omit the port in which case the default port for
134  * that service is assumed.
135  * However, some servers like IIS/OWA wrongly respond with a "404"
136  * instead of a "200" in case the port is appended. Because of this,
137  * ports 80 and 443 are not appended.
138  */
139  if (port == 80 || port == 443)
140  hostheader = g_strdup (hostname);
141  else
142  hostheader = g_strdup_printf ("%s:%d", hostname, port);
143 
144  url = build_encode_URL (keyword, NULL, item, "HTTP/1.1");
145  request = g_strdup_printf ("%s\r\n\
146 Connection: Close\r\n\
147 Host: %s\r\n\
148 Pragma: no-cache\r\n\
149 Cache-Control: no-cache\r\n\
150 User-Agent: %s\r\n\
151 Accept: image/gif, image/x-xbitmap, image/jpeg, image/pjpeg, image/png, */*\r\n\
152 Accept-Language: en\r\n\
153 Accept-Charset: iso-8859-1,*,utf-8\r\n",
154  url, hostheader, ua);
155  g_free (hostname);
156  g_free (hostheader);
157  g_free (ua);
158  g_free (url);
159  }
160  else
161  request = build_encode_URL (keyword, NULL, item, "HTTP/1.0\r\n");
162 
163  if (auth)
164  {
165  char *tmp = g_strconcat (request, auth, "\r\n", NULL);
166  g_free (request);
167  request = tmp;
168  }
169  if (data)
170  {
171  char content_length[128], *tmp;
172 
173  g_snprintf (content_length, sizeof (content_length),
174  "Content-Length: %zu\r\n\r\n", strlen (data));
175  tmp = g_strconcat (request, content_length, data, NULL);
176  g_free (request);
177  request = tmp;
178  }
179  else
180  {
181  char *tmp = g_strconcat (request, "\r\n", NULL);
182  g_free (request);
183  request = tmp;
184  }
185 
186  retc = alloc_typed_cell (CONST_DATA);
187  retc->size = strlen (request);
188  retc->x.str_val = request;
189  return retc;
190 }
191 
192 /*
193  * Syntax :
194  *
195  * http_get(port:<port>, item:<item>);
196  *
197  */
198 tree_cell *
200 {
201  return _http_req (lexic, "GET");
202 }
203 
204 /*
205  * Syntax :
206  *
207  * http_head(port:<port>, item:<item>);
208  *
209  */
210 tree_cell *
212 {
213  return _http_req (lexic, "HEAD");
214 }
215 
216 /*
217  * Syntax :
218  * http_post(port:<port>, item:<item>)
219  */
220 tree_cell *
222 {
223  return _http_req (lexic, "POST");
224 }
225 
226 /*
227  * http_delete(port:<port>, item:<item>)
228  */
229 tree_cell *
231 {
232  return _http_req (lexic, "DELETE");
233 }
234 
235 /*
236  * http_put(port:<port>, item:<item>, data:<data>)
237  */
238 tree_cell *
240 {
241  return _http_req (lexic, "PUT");
242 }
243 
244 /*-------------------[ cgibin() ]--------------------------------*/
245 
246 tree_cell *
247 cgibin (lex_ctxt *lexic)
248 {
249  const char *path = prefs_get ("cgi_path");
250  tree_cell *retc;
251 
252  (void) lexic;
253  if (path == NULL)
254  path = "/cgi-bin:/scripts";
255  retc = alloc_typed_cell (CONST_DATA);
256  retc->x.str_val = g_strdup (path);
257  retc->size = strlen (path);
258 
259  return retc;
260 }
nasl_close_socket
tree_cell * nasl_close_socket(lex_ctxt *lexic)
Definition: nasl_socket.c:905
script_infos
Definition: scanneraux.h:43
CONST_DATA
@ CONST_DATA
Definition: nasl_tree.h:93
vendor_version_get
const gchar * vendor_version_get()
Get vendor version.
Definition: vendorversion.c:52
plug_get_kb
kb_t plug_get_kb(struct script_infos *args)
Definition: plugutils.c:658
TC::str_val
char * str_val
Definition: nasl_tree.h:112
plug_get_host_fqdn
char * plug_get_host_fqdn(struct script_infos *args)
Definition: plugutils.c:211
nasl_http.h
TC::x
union TC::@2 x
get_str_var_by_name
char * get_str_var_by_name(lex_ctxt *, const char *)
Definition: nasl_var.c:1127
exec.h
name
const char * name
Definition: nasl_init.c:377
nasl_debug.h
nasl_perror
void nasl_perror(lex_ctxt *lexic, char *msg,...)
Definition: nasl_debug.c:120
http_close_socket
tree_cell * http_close_socket(lex_ctxt *lexic)
Definition: nasl_http.c:53
TC::size
int size
Definition: nasl_tree.h:109
cgibin
tree_cell * cgibin(lex_ctxt *lexic)
Definition: nasl_http.c:247
nasl_lex_ctxt.h
build_encode_URL
static char * build_encode_URL(char *method, char *path, char *name, char *httpver)
Definition: nasl_http.c:59
get_plugin_preference
char * get_plugin_preference(const char *oid, const char *name, int pref_id)
Get the a plugins preference.
Definition: plugutils.c:408
get_int_var_by_name
long int get_int_var_by_name(lex_ctxt *, const char *, int)
Definition: nasl_var.c:1113
nasl_open_sock_tcp_bufsz
tree_cell * nasl_open_sock_tcp_bufsz(lex_ctxt *lexic, int bufsz)
Definition: nasl_socket.c:417
nasl_func.h
struct_lex_ctxt::script_infos
struct script_infos * script_infos
Definition: nasl_lex_ctxt.h:41
http_post
tree_cell * http_post(lex_ctxt *lexic)
Definition: nasl_http.c:221
TC
Definition: nasl_tree.h:104
struct_lex_ctxt
Definition: nasl_lex_ctxt.h:33
nasl_var.h
http_delete
tree_cell * http_delete(lex_ctxt *lexic)
Definition: nasl_http.c:230
http_open_socket
tree_cell * http_open_socket(lex_ctxt *lexic)
Definition: nasl_http.c:47
_http_req
static tree_cell * _http_req(lex_ctxt *lexic, char *keyword)
Definition: nasl_http.c:75
nasl_global_ctxt.h
hostname
const char * hostname
Definition: pluginlaunch.c:76
http_head
tree_cell * http_head(lex_ctxt *lexic)
Definition: nasl_http.c:211
http_put
tree_cell * http_put(lex_ctxt *lexic)
Definition: nasl_http.c:239
http_get
tree_cell * http_get(lex_ctxt *lexic)
Definition: nasl_http.c:199
nasl_socket.h
alloc_typed_cell
tree_cell * alloc_typed_cell(int typ)
Definition: nasl_tree.c:40
nasl_tree.h