Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Adam Barth
On Tue, Nov 24, 2009 at 11:21 PM, Maciej Stachowiak m...@apple.com wrote:
 If we tie it to an element or attribute, people may be tempted to just do it
 in markup, which would be insecure.

Maybe we should have a DOM API called
webkitJailChildren(no-script-for-you) on Node that prevents future
children from running script.  Making it a DOM API prevents authors
from trying to turn the feature on with markup.

On Tue, Nov 24, 2009 at 11:27 PM, Michal Zalewski lcam...@google.com wrote:
 span secure_mode=$random_server_generated_nonce
 ...unsanitized user content...
 /span secure_mode=$random_server_generated_nonce

I'd rather not go this route in our initial implementation.  I think
we should target the use case of a web site receiving an untrusted
string via cross-origin XMLHttpRequest or postMessage.

Adam
___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Michal Zalewski
 http://lists.whatwg.org/htdig.cgi/whatwg-whatwg.org/2009-June/020191.html
 I think we should experiment with the minimal API that seems useful.
 If the experiment is a success, we can scale it up.

Apologies if I am rehashing something discussed earlier, but I think it
would be easy to run into some subtle problems with an API such as
.safeInnerHTML API, when mixed with .innerHTML.

The approach where input is sanitized upon assignment (and the
original is not stored anywhere) is possibly the best, but may still
lead to trouble. One possibility is the behavior of innerHTML on xmp
or textarea elements, which seems inconsistent and potentially dangerous
across browsers; and in general, innerHTML manipulation following
safeInnerHTML assignments seem like an easy way to accidentally mess
things up on web application side.

Deferred sanitization triggered by safeInnerHTML assignments is
another possibility, but it creates a whole lot other issues, e.g.:

foo.safeInnerHTML =  'a href=' + user_string + '.../a'
foo.innerHTML += 'brTa-dah!';

...or:

foo.safeInnerHTML =  'a href=' + user_string + '.../a'
bar.innerHTML = foo.safeInnerHTML;

Tainting elements that had their contents accessed via .safeInnerHTML,
and then tracking and propagating this data, is one way to avoid
problems - but it introduces significant complexity and would be
pretty opaque to developers; especially when dealing with .innerHTML
on outer or nested elements.

I think the syntax outlined in Adam's post is much safer, would
definitely require far fewer implementation-level challenges, and
would introduce fewer gotchas for web app developers by tying
sanitization to a well-defined output container, rather than one of
several content access methods.

More importantly, it is also easily extensible to a solution that
could be utilized by non-JS pages, as its logical 1:1 equivalent would
be a nonced, locked element, say:

span secure_mode=$random_server_generated_nonce
...unsanitized user content...
/span secure_mode=$random_server_generated_nonce

This is not a fortunate syntax, but illustrates the idea reasonably
well. The boundaries are guarded, so the approach is safe as long as
the server can produce decent random boundaries, and the benefit is
that server-generated pages can benefit from lightweight sanitization
without the need to do all content rendering dynamically with
client-side JS - which would make a huge difference.

/mz
___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Michal Zalewski
 I'd rather not go this route in our initial implementation.  I think
 we should target the use case of a web site receiving an untrusted
 string via cross-origin XMLHttpRequest or postMessage.

Fair enough. OTOH, this solves a very narrow problem. If we have an
implementation that at least extends to a non-JS solution without the
need to create a wholly separate mechanism should there eventually be
desire to make a difference in this area, it's a win. So, child-locked
tags appeal to me a whole lot more than a variant of .innerHTML.

Cheers,
/mz
___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Maciej Stachowiak


On Nov 25, 2009, at 6:05 AM, Adam Barth wrote:

On Tue, Nov 24, 2009 at 11:21 PM, Maciej Stachowiak m...@apple.com  
wrote:
If we tie it to an element or attribute, people may be tempted to  
just do it

in markup, which would be insecure.


Maybe we should have a DOM API called
webkitJailChildren(no-script-for-you) on Node that prevents future
children from running script.  Making it a DOM API prevents authors
from trying to turn the feature on with markup.


Interesting idea. This seems potentially trickier to implement than  
just innerStaticHTML, since nearly every method that mutates the DOM  
will have to check jail status. innerStaticHTML could be limited in  
scope to only operations that happen as part of parsing.


On Tue, Nov 24, 2009 at 11:27 PM, Michal Zalewski  
lcam...@google.com wrote:

span secure_mode=$random_server_generated_nonce
...unsanitized user content...
/span secure_mode=$random_server_generated_nonce


I'd rather not go this route in our initial implementation.  I think
we should target the use case of a web site receiving an untrusted
string via cross-origin XMLHttpRequest or postMessage.


One obvious likely use case is for sites that wish to sanitize user- 
generated content, for example comment sections of blogs.  
innerStaticHTML is actually decent for that use case. Not quite as  
nice as markup, but I'm wary of introducing parser complexity to  
defend against hostile content that tries to prematurely close the jail.


Regards,
Maciej

___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Maciej Stachowiak


On Nov 25, 2009, at 12:34 PM, Adam Barth wrote:

On Wed, Nov 25, 2009 at 12:30 PM, Maciej Stachowiak m...@apple.com  
wrote:

On Nov 25, 2009, at 6:05 AM, Adam Barth wrote:

Maybe we should have a DOM API called
webkitJailChildren(no-script-for-you) on Node that prevents future
children from running script.  Making it a DOM API prevents authors
from trying to turn the feature on with markup.


Interesting idea. This seems potentially trickier to implement than  
just
innerStaticHTML, since nearly every method that mutates the DOM  
will have to

check jail status. innerStaticHTML could be limited in scope to only
operations that happen as part of parsing.


Instead of checking every DOM mutation, we could just walk the parent
pointers before executing a script to see if an ancestor is jailed.



A few thoughts:

1) Presumably we'd want to block instantiation of plugins and Java  
applets too, or the scripting restriction becomes toothless. Perhaps  
also iframes, unless the scripting restriction is intended to  
propagate across frame boundaries.


2) Capturing all points at which script execution occurs and tracing  
them back to the originating element may be tricky. javascript: URIs  
are one potentially subtle example. By the time the JavaScript for  
those gets executed, I believe we no longer know the originating  
element, the way the code is currently structured.


3) It seems like the rule don't execute JS might not be quite what  
is desired, since it would (presumably) prevent the parent itself from  
using event listeners on nodes in the jail. IMO the best treatment for  
event listeners would be to prevent them from being created by  
attributes, rather than to prevent them from executing.


4) Do we need to strip or rename id, name and class values to prevent  
interference with the containing page's use of getElementById() and  
such? Caja does.


Regards,
Maciej

___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Adam Barth
On Wed, Nov 25, 2009 at 1:25 PM, Maciej Stachowiak m...@apple.com wrote:
 On Nov 25, 2009, at 12:34 PM, Adam Barth wrote:
 On Wed, Nov 25, 2009 at 12:30 PM, Maciej Stachowiak m...@apple.com wrote:
 On Nov 25, 2009, at 6:05 AM, Adam Barth wrote:
 Maybe we should have a DOM API called
 webkitJailChildren(no-script-for-you) on Node that prevents future
 children from running script.  Making it a DOM API prevents authors
 from trying to turn the feature on with markup.

 Interesting idea. This seems potentially trickier to implement than just
 innerStaticHTML, since nearly every method that mutates the DOM will have
 to
 check jail status. innerStaticHTML could be limited in scope to only
 operations that happen as part of parsing.

 Instead of checking every DOM mutation, we could just walk the parent
 pointers before executing a script to see if an ancestor is jailed.

I don't have a complete design in mind.  I could try to write up a
design document.

 A few thoughts:

 1) Presumably we'd want to block instantiation of plugins and Java applets
 too, or the scripting restriction becomes toothless. Perhaps also iframes,
 unless the scripting restriction is intended to propagate across frame
 boundaries.

Yes.  Also the base element.  Essentially, all the same APIs that
are currently restricted by the XSSAuditor.

 2) Capturing all points at which script execution occurs and tracing them
 back to the originating element may be tricky. javascript: URIs are one
 potentially subtle example. By the time the JavaScript for those gets
 executed, I believe we no longer know the originating element, the way the
 code is currently structured.

The way I would do this is to teach HTMLAnchorElement and friends not
to hand off JavaScript URLs to FrameLoader if their parent is jailed.
I'm not sure how many such interception points we'd need.

 3) It seems like the rule don't execute JS might not be quite what is
 desired, since it would (presumably) prevent the parent itself from using
 event listeners on nodes in the jail. IMO the best treatment for event
 listeners would be to prevent them from being created by attributes, rather
 than to prevent them from executing.

Agreed.  We'd want to stop inline event listeners from being created
on jailed nodes.

 4) Do we need to strip or rename id, name and class values to prevent
 interference with the containing page's use of getElementById() and such?
 Caja does.

I think this is an order of magnitude less important that direct
script execution.  There are going to be advanced use cases for which
Caja is the right answer.

The other way to skin this cat, by the way, is to implement the
seamless attribute on iframes.  That gives you a similar sort of
design using the @sandbox attribute and solves many of your above
concerns, e.g. by creating a new namespace for @ids.  Maybe we should
try that first or in parallel?

Adam
___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Michal Zalewski
 The other way to skin this cat, by the way, is to implement the
 seamless attribute on iframes.  That gives you a similar sort of
 design using the @sandbox attribute and solves many of your above
 concerns, e.g. by creating a new namespace for @ids.  Maybe we should
 try that first or in parallel?

I would think that in practice, IFRAMEs would, at least
psychologically, be significantly less useful to web app developers.

This is due to the fact that frames are conceptually more difficult to
properly position and size to accommodate any dynamically inserted
text; are more cumbersome to pre-populate with data on server-side
(extra HTTP roundtrips or opaque data: URLs). Also, are renderer
implementations actually ready to handle hundreds of seamless IFRAMEs
on a page with the performance footprint not exceeding that of spans
and divs?

/mz
___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Maciej Stachowiak


On Nov 25, 2009, at 1:33 PM, Adam Barth wrote:

On Wed, Nov 25, 2009 at 1:25 PM, Maciej Stachowiak m...@apple.com  
wrote:

On Nov 25, 2009, at 12:34 PM, Adam Barth wrote:
On Wed, Nov 25, 2009 at 12:30 PM, Maciej Stachowiak  
m...@apple.com wrote:

On Nov 25, 2009, at 6:05 AM, Adam Barth wrote:

Maybe we should have a DOM API called
webkitJailChildren(no-script-for-you) on Node that prevents  
future
children from running script.  Making it a DOM API prevents  
authors

from trying to turn the feature on with markup.


Interesting idea. This seems potentially trickier to implement  
than just
innerStaticHTML, since nearly every method that mutates the DOM  
will have

to
check jail status. innerStaticHTML could be limited in scope to  
only

operations that happen as part of parsing.


Instead of checking every DOM mutation, we could just walk the  
parent

pointers before executing a script to see if an ancestor is jailed.


I don't have a complete design in mind.  I could try to write up a
design document.


Sounds like we could use one given the potential complications.




A few thoughts:

1) Presumably we'd want to block instantiation of plugins and Java  
applets
too, or the scripting restriction becomes toothless. Perhaps also  
iframes,
unless the scripting restriction is intended to propagate across  
frame

boundaries.


Yes.  Also the base element.  Essentially, all the same APIs that
are currently restricted by the XSSAuditor.

2) Capturing all points at which script execution occurs and  
tracing them
back to the originating element may be tricky. javascript: URIs are  
one

potentially subtle example. By the time the JavaScript for those gets
executed, I believe we no longer know the originating element, the  
way the

code is currently structured.


The way I would do this is to teach HTMLAnchorElement and friends not
to hand off JavaScript URLs to FrameLoader if their parent is jailed.
I'm not sure how many such interception points we'd need.


Not sure either. Two others I can think of are SVGAElement and  
HTMLFormElement.




3) It seems like the rule don't execute JS might not be quite  
what is
desired, since it would (presumably) prevent the parent itself from  
using
event listeners on nodes in the jail. IMO the best treatment for  
event
listeners would be to prevent them from being created by  
attributes, rather

than to prevent them from executing.


Agreed.  We'd want to stop inline event listeners from being created
on jailed nodes.


4) Do we need to strip or rename id, name and class values to prevent
interference with the containing page's use of getElementById() and  
such?

Caja does.


I think this is an order of magnitude less important that direct
script execution.  There are going to be advanced use cases for which
Caja is the right answer.


Caja wants to let you actually run script in the jail without  
interfering with the containing page - I definitely don't think we  
should target that. But preventing the content from interfering with  
the containing page seems in-scope. I agree this particular threat is  
less risky than actual script execution.



The other way to skin this cat, by the way, is to implement the
seamless attribute on iframes.  That gives you a similar sort of
design using the @sandbox attribute and solves many of your above
concerns, e.g. by creating a new namespace for @ids.  Maybe we should
try that first or in parallel?


Indeed, it can cover some similar use cases. I don't know if it's good  
for comment sections - one iframe per comment would be quite  
heavyweight. If there is any active content *around* each comment  
(like edit or reply buttons) then you might not be able to use one for  
all of them. In such a case I think innerStaticHTML (or moral  
equivalent via jailed nodes) would be a more suitable solution. If you  
have only a small number of untrusted content regions then seamless  
iframes could be a good solution and it might be easier to be really  
confident of the implementation (since all cross-frame access of any  
kind is already doing a security check, and turning off scripting or  
plugins wholesale for a frame can be done in a very localized way).  
OTOH it would require render tree expertise to implement the layout  
aspects.


Regards,
Maciej

___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Maciej Stachowiak


On Nov 25, 2009, at 1:45 PM, Michal Zalewski wrote:


The other way to skin this cat, by the way, is to implement the
seamless attribute on iframes.  That gives you a similar sort of
design using the @sandbox attribute and solves many of your above
concerns, e.g. by creating a new namespace for @ids.  Maybe we should
try that first or in parallel?


I would think that in practice, IFRAMEs would, at least
psychologically, be significantly less useful to web app developers.

This is due to the fact that frames are conceptually more difficult to
properly position and size to accommodate any dynamically inserted
text;


Seamless iframes would address this first problem by participating in  
the layout of the containing page.



are more cumbersome to pre-populate with data on server-side
(extra HTTP roundtrips or opaque data: URLs). Also, are renderer
implementations actually ready to handle hundreds of seamless IFRAMEs
on a page with the performance footprint not exceeding that of spans
and divs?


But not these last two problems (though I think you can still  
document.write() into a sandboxed seamless iframe, making it not much  
less convenient than the staticInnerHTML solution).


Regards,
Maciej

___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-25 Thread Adam Barth
On Wed, Nov 25, 2009 at 1:49 PM, Maciej Stachowiak m...@apple.com wrote:
 On Nov 25, 2009, at 1:33 PM, Adam Barth wrote:
 I don't have a complete design in mind.  I could try to write up a
 design document.

 Sounds like we could use one given the potential complications.

I've sketched out a complete design here:

http://docs.google.com/Doc?id=dd4p8wc4_12sm65qbk4

I've given the participants in this thread write access so they can
add notes / ideas.  If you'd like write access, let me know.

Adam
___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-24 Thread Maciej Stachowiak


On Nov 24, 2009, at 7:14 PM, Adam Barth wrote:


In the below message to the WHATWG, Ian suggests that vendors
experiment with an API that makes it easier for web developers to
programmatically add static HTML content to their pages without XSSing
themselves:

http://lists.whatwg.org/htdig.cgi/whatwg-whatwg.org/2009-June/020191.html

I think we should do as he recommends.  If no one objects, I'll add
this to my list of things to work on.


I think innerStaticHTML is a good idea. Is there also a use case for  
the static equivalent of insertAdjacentHTML()?


 - Maciej

___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-24 Thread Adam Barth
On Tue, Nov 24, 2009 at 8:39 PM, Maciej Stachowiak m...@apple.com wrote:
 On Nov 24, 2009, at 7:14 PM, Adam Barth wrote:
 In the below message to the WHATWG, Ian suggests that vendors
 experiment with an API that makes it easier for web developers to
 programmatically add static HTML content to their pages without XSSing
 themselves:

 http://lists.whatwg.org/htdig.cgi/whatwg-whatwg.org/2009-June/020191.html

 I think we should do as he recommends.  If no one objects, I'll add
 this to my list of things to work on.

 I think innerStaticHTML is a good idea. Is there also a use case for the
 static equivalent of insertAdjacentHTML()?

I think we should experiment with the minimal API that seems useful.
If the experiment is a success, we can scale it up.

Michal suggested to me off-list and another possibility is to have an
API that works like this:

var jail = document.createElement(jail);
document.getElementById(foo);
jail.innerHTML = untrusted_string;

We could do something similar with attributes:

var jail = document.getElementById(foo);
jail.setAttribute(sandbox, yes-please);
jail.innerHTML = untrusted_string;

One of the nice things about using a DOM API is we don't have to worry
about crazy parsing issues.

Adam
___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev


Re: [webkit-dev] innerStaticHTML

2009-11-24 Thread Maciej Stachowiak


On Nov 24, 2009, at 10:37 PM, Adam Barth wrote:

On Tue, Nov 24, 2009 at 8:39 PM, Maciej Stachowiak m...@apple.com  
wrote:

On Nov 24, 2009, at 7:14 PM, Adam Barth wrote:

In the below message to the WHATWG, Ian suggests that vendors
experiment with an API that makes it easier for web developers to
programmatically add static HTML content to their pages without  
XSSing

themselves:

http://lists.whatwg.org/htdig.cgi/whatwg-whatwg.org/2009-June/020191.html

I think we should do as he recommends.  If no one objects, I'll add
this to my list of things to work on.


I think innerStaticHTML is a good idea. Is there also a use case  
for the

static equivalent of insertAdjacentHTML()?


I think we should experiment with the minimal API that seems useful.
If the experiment is a success, we can scale it up.

Michal suggested to me off-list and another possibility is to have an
API that works like this:

var jail = document.createElement(jail);
document.getElementById(foo);
jail.innerHTML = untrusted_string;

We could do something similar with attributes:

var jail = document.getElementById(foo);
jail.setAttribute(sandbox, yes-please);
jail.innerHTML = untrusted_string;

One of the nice things about using a DOM API is we don't have to worry
about crazy parsing issues.


If we tie it to an element or attribute, people may be tempted to just  
do it in markup, which would be insecure.


Regards,
Maciej


___
webkit-dev mailing list
webkit-dev@lists.webkit.org
http://lists.webkit.org/mailman/listinfo.cgi/webkit-dev