Recently a scan was run on one of our applications and it returned the following 1 security threats:
1.Cookies NotMarked As Secure::Cookie without Secure flag set
2.Cookie without HttpOnly flag set::Cookiewithout HttpOnly flag set
$this->cache_ptr = new CACHE($_COOKIE["sess"], 0, 0);
CACHE is an user built library that uses Sessions etc.
I am not sure about the right syntax to mark the cookie secure and set the cookie with HttpOnly flag. Also, this is a legacy application running in php 4.
Can someone please help me with this or point me to a resource?
EDIT:
I implemented Sven's recommendation. Is there a way I can test the secure functionality?
Also,Since I am using php4(which will have to be updated eventaully)
I cannot use httponly in the setcookie function.
So does that mean,I need to add the following line before setcookie function?
header("Set-Cookie: hidden=value; httpOnly");
will it intefere with my setcookie function?
use setcookie(). read about it here. Set the sixth parameter to true to make the cookie secure.
The code you are showing does not set the cookie. It might trigger setting a cookie, but essentially you must look at the CACHE class and see what's going on there.
You are looking for function calls of setcookie(), and if not found, for header('Set-Cookie...').
You'll have to change setcookie() to include all the default values for the optional parameters, until at the end you set the last two to true for secure and httponly.
Have a look at the manual: http://de1.php.net/setcookie
Related
I am trying to set a cookie with false in the secure parameter but when it is sent it always says secure/true. What could be causing my cookie setting to ignore that parameter?
setcookie( 'TEST', 'Testing', 0, C_PATH, C_DOMAIN, false );
Header:
Set-Cookie: TEST=Testing; path=/;HttpOnly;Secure
You also have the HttpOnly flag set - which is not on by default in PHP either. So it might be that these are added by your web server or something else between the client and PHP. Because PHP has no way of enabling these flags by default, you always have to set them explicitely for every setcookie call.
Yet I would recommend using both of them if you use them for PHP.
I'm guessing not, but is there a way to set a cookie in PHP without having to put ob_start() at the start of the output?
My problem is, that I am developing a class, which among others, needs to set a cookie. Now I can't tell the person who uses it "you have to make a new instance of the class before you make any output", cause that would be lame. So can I somehow pull it off?
See Headers already sent by PHP
The unprofessional workarounds listed there apply. Specifically:
<META HTTP-EQUIV="Set-Cookie"
CONTENT="cookievalue=xy;expires=Friday, 14-Dec-12 12:12:12 GMT; path=/">
Or use javascript and set document.cookie.
You cannot. Cookies are sent as part of the header, so if you've already sent the body, it's too late. Output buffering is the solution.
Perhaps you could use session variables instead.
This is my workround and is working fine for me.
// Force set cookie now
$_COOKIE['ref_url'] = $_SERVER['HTTP_REFERER'];
// Set cookie after refresh site
setcookie('ref_url', $_SERVER['HTTP_REFERER'], Affiliate::$cookieTime);
// Diplay $_COOKIE
var_dump($_COOKIE['ref_url']);
I only want the session cookie on www.website.tld and www.apps.website.tld, using ini_set if possible. Also i need to set all cookies i write to both subdomains only. I do not want www.imgs.website.tld to have the cookies. the php session one i'm kinda unsure of. The cookies i set my self my idea was to call SetBothCookie($name,$value,$time) a custom function.
function SetBothCookie($name,$value,$time)
{
setcookie($name, $value, $time, "", "www.website.tld", 1);
setcookie($name, $value, $time, "", "www.apps.website.tld", 1);
}
So i think i have the SetBothCookie part down, but wanted to see what others think of that code. The part i'm stuck on is having php set the session cookie on both sub domains. I'm using session_set_save_handler to override the default php session storage to store sessions in the database, so both servers can use the same session data. From my understanding is if i put Javascript that does http requests on the www.apps.website.tld to www.website.tld it won't allow them to happen, and i want that added security, so thats my reason of running only a part of the site on a subdomain.
This function should work but...
Using secure parameter in set_cookie() according to PHP manual
Indicates that the cookie should only
be transmitted over a secure HTTPS
connection from the client. When set
to TRUE, the cookie will only be set
if a secure connection exists. On the
server-side, it's on the programmer to
send this kind of cookie only on
secure connection (e.g. with respect
to $_SERVER["HTTPS"]).
So I suggest to remove 6th parameter of set_cookie() function.
Also, you can call this function before any output or it will throw a warning like
Warning: Cannot modify header
information - headers already sent by
(output started at ...) in ... on line XX
Using session_set_save_handler() is good solution to take control over session variables.
If you want cookies for entire domain just use "/" or ".website.tld" (with initial dot according to RFC 2109 standard) for domain parameter (5th in a row). Parameter path should be "" (empty string; 4th).
In my framework, I make a number of calls to session_write_close().
Let's assume that a session has been initiated with a user agent. The following code...
foreach($i = 0; $i < 3; $i++) {
session_start();
session_write_close();
}
...will send the following request header to the browser:
Set-Cookie PHPSESSID=bv4d0n31vj2otb8mjtr59ln322; path=/
PHPSESSID=bv4d0n31vj2otb8mjtr59ln322; path=/
There should be no Set-Cookie header because, as I stipulated, the session cookie has already been created on the user's end. But every call to session_write_close() after the first one in the script above will result in PHP instructing the browser to set the current session again.
This is not breaking my app or anything, but it is annoying. Does anyone have any insight into preventing PHP from re-setting the cookie with each subsequent call to session_write_close?
EDIT
The problem seems to be that with every subsequent call to session_start(), PHP re-sets the session cookie to its own SID and sends a Set-Cookie response header. But why??
PHP does not recommend doing so, and there were bunch of bugs submitted for this. Since they think it's not a good practice - this is the bug that is not going to be fixed.
Almost every answer I found on SO says to just do a session_write_close() and session_start() over and over again...some even disable cookies with ini_set temporarily...this seems to be a very bad approach. The PHP authors provided a very clear, best-practice, path to injecting your own way of handling the sessions using session_set_save_handler.
I have created an example on another post that shows how you can replace your session_start() with Session::start() and replace session_write_close() with Session::save(). The class is a non-blocking (a user can have concurrent requests) class implemented for PHP 5.4+. In fact, it's just a tweaked version of PHP's example class.
While my example is PHP 5.4+, the same method works in older versions of PHP with callback methods instead of an interface implementation.
https://stackoverflow.com/a/27993746/482256
session_write_close just close session and write data
while session_start send cookies
if your don`t want send session cookie your mustn't call session_start
I would like to do the following in php :
setcookie('name', $value, $Cookie_Expiration,'/');
then some action
header("location:http://www.example.com")
the problem is that I get :
warning: Cannot modify header information - headers already sent by (...etc )
could you please let me know what i am doing wrong and if there is a way to do this?
by the way , this code is before any output is made ...the cookie setting part works fine on its own and so does the redirection code....the combination fails
thank you
Cookies are sent in the header, and you can't set headers if any output is already sent to the browser (which is is when you set the cookie).
The easiest solution, mind you it is a bit sloppy is to use ob_start() and ob_clean(), for example:
ob_start();
setcookie('name', $value, time()+3600);
ob_clean();
header("Location:http://www.example.com");
Please note the upper case L in the Location header, it is very important.
A better solution might be to set the cookie on the page you are redirecting to, and pass the information to set that header through a session.
From the php manual:
setcookie() defines a cookie to be sent along with the rest of the HTTP headers. Like other headers, cookies must be sent before any output from your script (this is a protocol restriction). This
requires that you place calls to this function prior to any output, including and tags as well as any whitespace.
basically saying what you already know from your warning; that the setcookie is itself sending a header. I'd probably wonder why you want to set a cookie on a page then redirect, why not just redirect and include the data in the URL then pick it up on the target page and use the data there and/or store it in a cookie then, or store in session data if you have a session set already.