Project

General

Profile

[Answered] mod_ssi, <!--#include virtual="/cgi-bin/Myscript.pl"-->: serves up content of script rather than result of executing it.

Added by bwechner almost 7 years ago

Am wondering what config I'm missing. I have mod_ssi loaded, and a single line file index.shtml with this line in it:

<!--#include virtual="/cgi-bin/Myscript.pl"-->

Here's my config:

$ lighttpd -p -f /etc/lighttpd/lighttpd.conf 
config {
    var.PID                        = 13380
    var.CWD                        = "/mnt/passport/www/html/bernd.wechner.info/Hitchhiking/Suite101" 
    mimetype.assign                = (
        ".ez"       => "application/andrew-inset",
         ...
        ".vrm"      => "x-world/x-vrml",
        # 517
    )
    server.document-root           = "/var/www/html" 
    server.upload-dirs             = ("/var/cache/lighttpd/uploads")
    server.errorlog                = "/var/log/lighttpd/error.log" 
    server.pid-file                = "/var/run/lighttpd.pid" 
    server.username                = "www-data" 
    server.groupname               = "www-data" 
    server.port                    = 80
    debug.log-condition-handling   = "enable" 
    index-file.names               = ("index.php", "index.shtml", "index.html", "index.lighttpd.html")
    url.access-deny                = ("~", ".inc")
    static-file.exclude-extensions = (".php", ".pl", ".fcgi")
    compress.cache-dir             = "/var/cache/lighttpd/compress/" 
    compress.filetype              = ("application/javascript", "text/css", "text/html", "text/plain")
    accesslog.filename             = "/var/log/lighttpd/access.log" 
    cgi.assign                     = (
        ".pl" => "/usr/bin/perl",
        ".py" => "/usr/bin/python",
        # 2
    )
    server.modules                 = (
        "mod_access",
        "mod_alias",
        "mod_compress",
        "mod_redirect",
        "mod_accesslog",
        "mod_cgi",
        "mod_ssi",
        # 7
    )
    ssi.extension                  = (".shtml")

    $SERVER["socket"] == "[::]:80" {
        # block 1

    } # end of $SERVER["socket"] == "[::]:80" 

    $HTTP["url"] =~ "^/cgi-bin/" {
        # block 2
        cgi.assign = (
            ".pl" => "/usr/bin/perl",
            ".py" => "/usr/bin/python",
            # 2
        )

    } # end of $HTTP["url"] =~ "^/cgi-bin/" 
}

Now the page loads fine, it just renders the perl script is all, not the result of running it. The script has execute permission (for owner, group and world for now while testing), I can run it from bash and it produces the HTML I'd like sent to the browser, but instead lighttpd is sending "cat /cgi-bin/Myscript.pl" to my browser)

I have a feeling there is some simple config thing I'm missing. But what puzzles me most is that

static-file.exclude-extensions = (".php", ".pl", ".fcgi")

should really be preventing the script being served up as a static file.

Any pointers would be deeply appreciated.

Kind regards,

Bernd.


Replies (4)

RE: mod_ssi, <!--#include virtual="/cgi-bin/Myscript.pl"-->: serves up content of script rather than result of executing it. - Added by gstrauss almost 7 years ago

Am wondering what config I'm missing.

Unfortunately, lighttpd mod_ssi <!--#include virtual=...> only operates on url-path to SSI file includes. mod_ssi does not create a new request for each virtual, and therefore no other modules are involved in processing the virtual include. In other words, mod_cgi or other modules (include mod_staticfile) never get a chance to see the subrequest (because there is no subrequest). This also answers your questions why static-file.exclude-extensions (from mod_staticfile) is ignored.

Sorry, this is a limitation in lighttpd mod_ssi. lighttpd mod_ssi can help you paste together various files, but other processing is limited.

RE: mod_ssi, <!--#include virtual="/cgi-bin/Myscript.pl"-->: serves up content of script rather than result of executing it. - Added by bwechner almost 7 years ago

I've made a little progress testing this and it looks a lot like:

  1. SSI is not a good interface to use as introduced here: https://redmine.lighttpd.net/projects/lighttpd/wiki/Docs_ModSSI
  2. mod_ssi is buggy. Or well has "features" that aren't compatible with the way Apache implemented them.

Looks like I'll have to fix this port from Apache a little rather than just copy it over and see it work. Up side is it's only a trivially small amount of cgi to retweak. But here is what I'm seeing:

I have a simple Perl script (used mainly for testing):

$ cat printenv.pl
#!/usr/bin/perl

print "Content-type: text/html\n\n"; 

foreach $key (keys %ENV) {
    print "<li>$key: $ENV{$key}";
}

And a simple shtml file:

$ cat printenv-include.shtml 
<META http-equiv="expires" content="0">
<!--#include virtual="/cgi-bin/printenv.pl"-->

Now if I load printenv.pl in the browser I see:

URL: http://mysite/cgi-bin/printenv.pl

SERVER_PROTOCOL: HTTP/1.0
HTTP_ACCEPT_LANGUAGE: en-US,en;q=0.5
SERVER_SOFTWARE: lighttpd/1.4.35
HTTP_ACCEPT_ENCODING: gzip, deflate
REMOTE_ADDR: 192.168.0.1
SERVER_PORT: 80
DOCUMENT_ROOT: /var/www/...
HTTP_X_HOST: ...
HTTP_X_FORWARDED_FOR: 192.168.0.11
SCRIPT_FILENAME: /.../cgi-bin/printenv.pl
HTTP_UPGRADE_INSECURE_REQUESTS: 1
GATEWAY_INTERFACE: CGI/1.1
SCRIPT_NAME: /cgi-bin/printenv.pl
HTTP_HOST: mysite
REQUEST_METHOD: GET
CONTENT_LENGTH: 0
REMOTE_PORT: 35258
HTTP_CONNECTION: close
HTTP_ACCEPT: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
REQUEST_URI: /cgi-bin/printenv.pl
HTTP_USER_AGENT: Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:53.0) Gecko/20100101 Firefox/53.0
HTTP_X_FORWARDED_PROTO: http
REDIRECT_STATUS: 200
SERVER_ADDR: 0.0.0.0
SERVER_NAME: mysite

So it runs fine. Then if I load printenv-include.shtml I see:

URL:http://mysite/printenv-include.shtml

#!/usr/bin/perl print "Content-type: text/html\n\n"; foreach $key (keys %ENV) { print " 
$key: $ENV{$key}"; }

Yet the SSI docs I read here: https://en.wikipedia.org/wiki/Server_Side_Includes

Clearly state that I should see the same, the output of the CGI script. And the mod_ssi docs here: https://redmine.lighttpd.net/projects/lighttpd/wiki/Docs_ModSSI

Clearly state exec is enabled by default (though if I enable it explicitly with:

ssi.exec = 1

Nothing changes. Out of interest I wrote another page:

$ cat printenv-exec.shtml 
<META http-equiv="expires" content="0">
<!--#exec cmd="/cgi-bin/printenv.pl"-->

And it just returns a blank page if navigate to that. The doc on wikipedia is not clear if exec cmd output is included, but suspect it's not, and blank is what we should expect.

Still, on the face of it, it seems mod_ssi is broken, and probably no-one noticed, cares or will fix it, because it's a dated interface with strong recommendations to avoid.

To wit, I shall probably have to re-implement the 7 .shtml files on this site I'm porting to use standard cgi or fastcgi. Oh well.

On the off chance I'm wrong, by all means yell out, and let me know what can convince mod_ssi to include the output of cgi scripts as Apache does and not the content of the script (which seems an odd thing to do, rather at odds with the most rudimentary security concerns).

Regards,

Bernd.

RE: [Answered] mod_ssi, <!--#include virtual="/cgi-bin/Myscript.pl"-->: serves up content of script rather than result of executing it. - Added by gstrauss almost 7 years ago

mod_ssi is buggy. Or well has "features" that aren't compatible with the way Apache implemented them.

"not implemented" is different from a feature and is different from a bug.
"not implemented" is, well, not implemented. You may reasonably consider this buggy behavior, but I am not interested in arguing over the semantics.

Also, lighttpd is not Apache and lighttpd does not claim to be compatible with Apache, although lighttpd often follows widely accepted web server conventions. This obviously does not apply to any "not implemented" case.

probably no-one noticed, cares or will fix it, because it's a dated interface with strong recommendations to avoid.

It is known, but it is not a priority. As I have said elsewhere and multiple times in the forums, if someone codes up a patch, I will review it seriously, though I do not make any promise to accept just any/all patches into the lighttpd base.

.

Your use of @ is incorrect since you wrongly assumed you could use the virtual path there. If you look at https://en.wikipedia.org/wiki/Server_Side_Includes again, you'll see that #exec cmd= takes a filesystem path to the command to execute. Before you ask, lighttpd does not implement #exec cgi=@

RE: mod_ssi, <!--#include virtual="/cgi-bin/Myscript.pl"-->: serves up content of script rather than result of executing it. - Added by bwechner almost 7 years ago

gstrauss wrote:

Am wondering what config I'm missing.

Unfortunately, lighttpd mod_ssi <!--#include virtual=...> only operates on url-path to SSI file includes. mod_ssi does not create a new request for each virtual, and therefore no other modules are involved in processing the virtual include. In other words, mod_cgi or other modules (include mod_staticfile) never get a chance to see the subrequest (because there is no subrequest). This also answers your questions why static-file.exclude-extensions (from mod_staticfile) is ignored.

Sorry, this is a limitation in lighttpd mod_ssi. lighttpd mod_ssi can help you paste together various files, but other processing is limited.

Thanks for the update, sorry didn't notice it sooner. Indeed it seems mod_ssi doesn't provide SSi compatibility with standards of the bygone era, and as noted after my tests, is a botch and as per its own documentation best avoided ;-).So I have 7 shtml files to reconstruct as plain CGI's perhaps or some such. Not a huge job, just a bother ;-).

    (1-4/4)