views:

244

answers:

4

I am working through an older php mysql book written in 2003. The author uses the include() function to construct html pages by including header.inc, footer.inc, main.inc files, etc. Now I find out that this is not allowed in the default ini settings, (allow_url_include is set to Off) after I got many warnings from the server.

I noticed also that you can use include without the parenthesis. I tried this and it works and I get no error messages or warnings. Are the two different? That is, is include() different from include ?

+16  A: 

This is a misunderstanding. You can turn off the inclusion of remote files (using a URL http://www.example.com/include.php instead of a filesystem path). You can always include local files.

The latter is because include is not a normal function, but a language construct. Like die, it can be used with or without parentheses. Source: Manual

Because include() is a special language construct, parentheses are not needed around its argument. Take care when comparing return value.

Pekka
How is this a security answer? (This question has a security tag...)
Rook
@The Rook I don't see any indication that the OP is asking about the use of variables for include names. I think the `security` tag was added due to the `allow_url_include` aspect.
Pekka
Are there specific times when you do use the parentheses and others when you do not? Is there a standard practice of using them or not? Is there a reason that they are not needed? Is it to set them apart from other functions that are not Control Structures?
aliov
@aliov I can't think of a situation where it makes a difference but for the sake of homogeneous code, I would go with the brackets.
Pekka
+3  A: 

The use of include() can introduce a Local File Include (LFI) or Remote File Include(RFI) Vulnerably. You should try and avoid using include, for instance if you are including HTML its better to write print(file_get_contents($file)) than include($file). However include()'ing PHP files is necessary in most php applications to reduce code duplication.

Even when remote file inclusion is disabled its still possilbe to exploit the system using an Advanced LFI Attack.

If you do need to accept user input in an include(), then you should make sure its on a white list:

$good_includes=array("contact","home","view");
if(in_array($_GET[page],$good_includes)){
    include("inc/".$_GET[page].".php");
}
Rook
Why was this voted down? Might still be relevant for the examples from the questioners book. And it's interesting anyway.
mario
print(file_get_contents($file)) than include($file) are not exactly interchangeable and the links included refer to usage of unvalidated data in the include statements, which is stupid and has damage potential both for file_get_contents and include. Downvoted.
Artefacto
@Artefacto **...if you are including HTML...**
Rook
@The Root If you are including HTML you should use file_get_contents instead of include, but that's for performance reasons, not security reasons. If you use unvalidated data in the file_get_contents argument you are only slightly better off. Anyway, I reversed the vote; I confess I hadn't read the "including HTML" passage.
Artefacto
@Artefacto Yes, it is still a vulnerability, however my point is that a remote file disclosure vulnerability is less dangerous than a remote code execution venerability. After all the question is "why should i not use include", and my answer is you should **NOT** use it for html.
Rook
Upvoted. Good answer.
GlenCrawford
@GlenCrawford thank you.
Rook
I don't think this was what the OP asked for, but +1 nevertheless. You can't stress this too often.
Pekka
Let's see if I understand all of this correctly. If and when I use include with a URL as in the following:include('http://www.site.com/file.xxx'), (even if the url points to a file on my own site), my server throws up this warning:Warning: include() [function.include]: URL file-access is disabled in the server configurationThis is because the allow_url_include ini setting is turned to off and should not be overridden because of security reasons.
aliov
When saying, "if you are including html", does this mean an actual .html file, or a URL that could point to a file of any extension?
aliov
Also, when you say, "If you do need to accept user input in an include(), then you should make sure its on a white list:", does this mean the included portion of the page or any part of the page with an include on it? For example: I include a file called register.php which of course would have code that would require user input in order to register to the site. This is a NO NO. ? The other example would be: I have a page titled register .php which has include sections - header, footer, etc. This is OK. ?
aliov
Is validating user input as secure as putting it on a white list?Is there a time when I would use one over the other?
aliov
A: 

There's a major difference with include/require_once and require.

The primary difference is the error reporting, if you use include in your application PHP will attempt to load the file but if it does not exist, it will throw non fatal error (meaning you script will not halt), if you are using require then the script will halt and stop processing.

Use require on files that are fundamental to your application and use include in your templates because if there is an error you can specify not to show the error and thus the user will not know the difference as long as its not a primary template include such as header.php

these functions are mainly used on your own server to include files that are relevant to your application.

if you are including files from outside your server then I would use curl if it's installed or file_get_contents().

Hope this helps you.

just a note on require vs require_once, require_once will add logic to make sure that file is not included more than once, ie you don't want to declare your database connection more than once

RobertPitt
Doesn't address the actual issue =/
Matchu
downvote for being completely lateral to the question.
Artefacto
A: 

Function include is good for dynamic inckuding of files. If we include files in cycle, this very good. But if we include files staticly, we should use require. Second function do in the beginnig of script.

Alexander.Plutov