Google’s School for Hackers

Google is offering programmers their own personal sandbox application—called Jarlsburg—and hints of how to exploit the common vulnerabilities purposefully left in it. Although Google is basically walking folks through how to attack apps, publicizing this info is a necessary evil in order to build safer programmers. We have to start thinking of each line of code, cookie, HTTP request, and configuration option as another attack surface.

The table of contents lists the who’s who of vulnerabilities (though there are a lot more out there). Several of these attacks no one would’ve even dreamed of a few years ago, so the sad reality is that the web is chock full of vulnerable “legacy” apps just waiting to be exploited—unless we can fix them in time.

  • Cross-Site Scripting (XSS)
    • XSS Challenges
    • File Upload XSS
    • Reflected XSS
    • Stored XSS
    • Stored XSS via HTML Attribute
    • Stored XSS via AJAX
    • Reflected XSS via AJAX
    • More about XSS
  • Client-State Manipulation
    • Elevation of Privilege
    • Cookie Manipulation
  • Cross-Site Request Forgery (XSRF)
    • XSRF Challenge
    • More about preventing XSRF
  • Cross Site Script Inclusion (XSSI)
    • XSSI Challenge
  • Path Traversal
    • Information disclosure via path traversal
    • Data tampering via path traversal
  • Denial of Service
    • DoS – Quit the Server
    • DoS – Overloading the Server
    • More on Denial of Service
  • Code Execution
    • Code Execution Challenge
    • More on Remote Code Execution
  • Configuration Vulnerabilities
    • Information disclosure #1
    • Information disclosure #2
    • Information disclosure #3
  • AJAX vulnerabilities
    • DoS via AJAX
    • Phishing via AJAX
  • Other Vulnerabilities
    • Buffer Overflow and Integer Overflow
  • SQL Injection

Uh-Oh: Firefox’s Unique Session Cookie Behavior

By now, Opera’s invention of restoring tabs automatically is available in most browsers, but unlike every other browser, Firefox’s restored tabs retain session cookies for the domains of the saved tabs Firefox restores all session cookies as if the browser were never closed. This is handy in some ways, but dangerous in others:

It’s fooling web developers by breaking a very old and widely-known convention. Since Netscape’s original spec (around 1994) a cookie with an empty/missing expires was to be discarded “when the user’s session ends” (later clarified as “when the user agent exits” in RFC2109), and thousands of prominent web pages describe “session cookies” this way.

A common session design pattern uses a persistent cookie to establish low-level identity info and a session cookie for full authentication. Developers may not know that their full auth period may be lasting days or weeks, including trips to insecure wifi spots, browsing by multiple users, etc.

It’s fooling users. No one thinks of a single browsing “session” as encompassing several days of browser usage just because the same tabs were open, and users frequently read that they need to simply exit their browser to ensure their session is ended.

Recommendations

  • Be aware that Firefox session cookies can linger for days, despite the user having closed their browser.
  • Manage session timeouts on the server-side and/or via HMAC-signed timestamp values in the cookie contents (don’t let the client decide how long a session should last).
  • If you can, include secure in the cookie header. Firefox does not restore HTTPS session cookies. Realize that in later FF versions, “secure” cookies also are restored.
  • If you give out session cookies with unique names, have your application clean these up when they’re no longer needed. If you don’t, your Firefox users could suffer from…

Cookie Accumulation Torment

This annoying situation occurs when Firefox gains so many local cookies that the web server begins to deny all your requests. Deleting some or all these cookies is the only way to fix the issue because—yay—the problem session cookies persist across browser, and even OS, restarts.

Big Shibboleth Implications

If your Shibboleth-authenticating app maintains its own session, make sure that the “sign out” function searches for and deletes the local Shibboleth cookies (or that the SP sets only “secure” cookies). Otherwise this could happen:

  1. Jane “signs out”, closes Firefox, and lends her computer to Sally.
  2. Sally opens Firefox and clicks “sign in”.
  3. Sally is instantly authenticated into Jane’s account!

Jane’s application session was over, but Firefox allowed her Shibboleth session to live on.

Also, since Shibboleth gives out uniquely-named session cookies (prepended with _shibstate), failing to clean these up will lead Firefox users to the aforementioned torment. If the user has an app open all day every day, count on her gaining at least one cookie per day.

Elgg, ElggChat, and Greener HTTP Polling

At my new job, we maintain a site powered by Elgg, the PHP-based social networking platform. I’m enjoying getting to know the system and the development community, but my biggest criticisms are related to plugins.

On the basis of “keeping the core light”, almost all functionality is outsourced to plugins, and you’ll need lots of them. Venturing beyond the “core” plugins—generally solid, but often providing just enough functionality to leave you wanting—is scary because generally you’re tying 3rd-party code into the event system running every request on the site. Nontrivial plugins have to provide a lot of their own infrastructure and this seems to make it more likely that you’ll run into conflict bugs with other plugins. With Elgg being a small-ish project, non-core plugins tend to end up not well-maintained, which makes the notion of upgrading to the latest Elgg version a bit scary when there have been API changes. Then there’s the matter of determining in what order your many plugins sit in the chain; order can mean subtle differences in processing and you just have to shift things around hoping to not break something while fixing something else. Those are my initial impressions anyway, and no doubt many other open source systems relying heavily on plugins have these problems. There’s a lot of great rope to hang yourself with.

Jeroen Dalsem’s ElggChat seems to be the slickest chat mod for Elgg. Its UI more or less mirrors Facebook’s chat, making it instantly usable. It’s a nice piece of work. Now for the bad news (as of version 0.4.5):

  • Every tab of every logged in user polls the server every 5 or 10 seconds. This isn’t a design flaw—all web chat clients must poll or use some form of comet (to which common PHP environments are not well-suited)—but other factors make ElggChat’s polling worse than it needs to be:
  • Each poll action looks up all the user’s friends and existing chat sessions and messages and returns all of that in every response. If the user had 20 friends, a table containing all 20 of them would be generated and returned every 5 seconds. The visible UI would also become unwieldy if not unusable.
  • The poll actions don’t use Elgg’s “action token” system (added in 1.6 to prevent CSRFs). This isn’t much of a security flaw, but in Elgg 1.6 it fills your httpd logs with “WARNING: Action elggchat/poll was called without an action token…” If you average 20 logged in users browsing the site, that’s 172,800 long, useless error log entries (a sea obscuring errors you want to see) per day. Double that if you’re polling at 5 seconds.
  • The recent Elgg 1.7 makes the action tokens mandatory so the mod won’t work at all if you’ve upgraded.
  • Dalsem hasn’t updated it for 80 days, I can’t find any public repo of the code (to see if he’s working on it), and he doesn’t  respond to commenters wondering about its future.

The thought of branching and fixing this myself is not attractive at the moment, for a few reasons (one of which being our site would arguably be better served by a system not depending on the Elgg backend, since we have content in other systems, too), but here are some thoughts on it.

Adding the action token is obviously the low hanging fruit. I believe I read Facebook loads the friends and status list only every 3 minutes, which seems reasonable. That would cut most of the poll actions down to simply maintaining chat sessions. Facebook’s solution to the friends online UI seems reasonable: show only those active, not offline users.

“Greener” Polling

Setting aside the ideal of comet connections, one of the worst aspects of polling is the added server load of firing up server-side code and your database for each of those extra (and mostly useless) requests. A much lighter mechanism would be to maintain a simple message queue via a single flat file, accessible via HTTP, for each client. The client would simply poll the file with a conditional XHR GET request and the httpd would handle this with minimal overhead, returning minimal 304 headers when appropriate.

In its simplest form, the poll file would just be an alerting mechanism: To “alert” a client you simply place a new timestamp in its poll file. On the next poll the client will see the timestamp change and immediately make another XHR request to fetch the new data from the server-side script.

Integrating this with ElggChat

In ElggChat, clicking a user creates a unique “chatsession” (I’m calling this “CID”) on the server, and each message sent is destined for a particular CID. This makes each tab in the UI like a miniature “room”, with the ability to host multiple users. You can always open a separate room to have a side conversation, even with the same user.

In the new model, before returning the CID to the sender, you’d update the poll files of both the sender and recipient, adding the CID to each. When the files are modified, you really need to keep only a subset of recent messages for each CID. Just enough to restore the chat context when the user browses to a new page. The advantage is, all the work of maintaining the chat sessions and queues is only done when posts are sent, never during the many poll requests.

Since these poll files would all be sitting in public directories, their filenames would need to contain an unguessable string associated with each user.

IE9 May Raise the Bar

Wow.

IE9 passing a bunch of tests

IE9 is coming, and it looks like it’ll get Microsoft back in the game. Full Developer Guide.

The Good: New standards supported, hardware-accelerated canvas, SVG, Javascript speed on par with the other browsers, preview installs side-by-side with IE.

The Bad: Not available on XP and no guarantee it will be. XP users will be stuck with, you know, all the other browsers that run their demos fine.

“Scary Web Error!”

Apparently on a few AT&T phones, a few Facebook users were dropped into accounts of other users.

After typing Facebook.com into her Nokia smart phone, she was taken into the site without being asked for her user name or password. She was in an account that didn’t look like hers.

… AT&T spokesman Michael Coe said its wireless customers have landed in the wrong Facebook pages in “a limited number of instances” and that a network problem behind those episodes is being fixed … Coe said an investigation points to a “misdirected cookie.” …  Coe said technicians couldn’t figure out how the cookie had been routed to the wrong phone…

Well that’s a new one. Sites could store the UA string in the server-side session on login and make sure it doesn’t change. This would prevent the auto-logged-in-as-other-user problem (except for users with identical phones), but, despite this being a sensible security option, I don’t think many sites do it. If these problems start becoming more common that may need to change.

Configuring Sendmail for UF’s SMTP

Our Ubuntu web host, hosted with OSG, was not able to send mail (using PHP mail) outside of UF. An OSG tech said our From: header should be a valid address at UF (check) and that the logs at smtp.ufl.edu showed those messages never made it there.

The solution was to configure sendmail to use smtp.ufl.edu as the “smart” relay host (as it’s described in the config file):

$ sudo nano /etc/mail/sendmail.cf

Ctrl+w and search for smart. On the line below, add smtp.ufl.edu directly after DS with no space. The result should be:

# "Smart" relay host (may be null)
DSsmtp.ufl.edu

Ctrl-x and save the buffer.

Restart sendmail: $ sudo /etc/init.d/sendmail restart

As soon as I did this, the queued messages were sent out. I still don’t know why messages to ufl.edu succeeded while others sat in the queue.

Get higher quality images within printed web pages

Due to web images being optimized for on-screen display (let’s say 96 DPI), images on printed pages are usually blurry, but they don’t have to be:

  1. Start with a high-resolution image. E.g. 2000 x 1000.
  2. Save a version with dimensions that fit well in your printed layout when placed in an IMG element. E.g. 300 x 150.
  3. In your print CSS, fix the size of the IMG element in pixels to match the dimensions in (2).
  4. Using the original image, recreate the image file in (2) with significantly larger dimensions (identical width/height ratio). E.g. 600 x 300.

The Good News: The printed page will have an identical layout as in (2), but with a higher quality image. This is because–according to my testing–even browsers that use blocky “nearest neighbor” image scaling for screen will scale nicely for print.

The Bad News: Continue reading  

Call it “SecondOpinion”

The creators of StackOverflow should team up with the Dept. of Health & Human Services and launch a medical Q&A site based on the SO model.

StackOverflow was designed by a few programmers to scratch an itch within the community, and the model they came up with made it the most effective question/answer site I’ve ever used. Got a really, really tough programming question? You can probably get a half dozen answers in 5 or 10 minutes, and if you wait a day, you can see them ranked by quality by several programmers within your field.

As medical professionals contributed answers, comments, and votes in their spare time, a medical version of SO would quickly turn into an amazing resource for public health.

It might require some tweaking. SO users are generally in the same community, though sometimes different specialties. This makes it easier to design behavior-reinforcing tricks to keep user contributing. Every time I get a question answered I almost always end up taking a few minutes to provided input to other questions, and I earn points and “badges” for contributing (what other users deem as) good info.

On a medical Q&A site the advice takers and givers are mostly exclusive communities, but I think professionals would still contribute, and we could create ways to encourage them. Medical schools could require students to earn points on the site; we could reward consistently good contributors financially or with real awards.