Cenzic 232 Patent
Paid Advertising
sla.ckers.org is
ha.ckers sla.cking
Sla.ckers.org
Q and A for any cross site scripting information. Feel free to ask away. 
Go to Topic: PreviousNext
Go to: Forum ListMessage ListNew TopicSearchLog In
Pages: Previous1234567891011...LastNext
Current Page: 4 of 13
Re: JSReg sandbox challenge
Posted by: kangax
Date: July 30, 2009 12:59PM

Quote

My problem is this:-
var Number = function(v) { this.x=function() { alert(1); }; this.valueOf=function() { return v } };
Number.prototype=window.Number;
(new Number(1)+new Number(1)).x()// is not called :(

Yeah. `(new Number(1))` is your object here, but addition operator invokes this object's `valueOf`, which returns `1` (of type Number, of course). Same happens with another operand and so you end up with `1 + 1`, producing `2`. Then property accessor ('.') kicks in, turns primitive `2` into a corresponding Number object and starts looking for 'x' up the proto-chain - first in `Number.prototype`, then in `Object.prototype`. Since `x` is not on any of those, it evaluates to `undefined` and so call operator ("()") rightfully throws TypeError :)

Quote

also: typeof new Number(1) === 'object' // :(

Works as designed :) See http://bclary.com/2004/11/07/#a-15.7.2.1

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: July 30, 2009 02:54PM

Yeah that's what I thought :( damn.

Well it works now because I use the Number() constructor but I add to the prototype. Maybe I'll have to create a new window and read the code into that to make private prototypes

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: kangax
Date: July 31, 2009 08:48AM

Gareth, in case you don't know, Mozilla finally got around to taking care of the negative indices hole that you blogged about https://bugzilla.mozilla.org/show_bug.cgi?id=507453

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: July 31, 2009 08:52AM

@kangax

Sniff, sniff, yep I know. Well it was fun while it lasted :) Now we've got to find something different to play with

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: sirdarckcat
Date: July 31, 2009 04:39PM

Did u know that "working threads" in firefox 3.5 work as a sandbox? website-land sandbox!

--------------------------------
http://sirdarckcat.blogspot.com/ http://www.sirdarckcat.net/ http://foro.elhacker.net/ http://twitter.com/sirdarckcat

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: sirdarckcat
Date: July 31, 2009 04:42PM

oh! and the...
while(1)alert(1)

is looping for ever... that ruined one demo at blackhat haha..

it wasnt very crowded, but the mozilla security guys, and dross, some friends and the ocassional peekers were watching an endless loop looping for ever..

Greetz!!

--------------------------------
http://sirdarckcat.blogspot.com/ http://www.sirdarckcat.net/ http://foro.elhacker.net/ http://twitter.com/sirdarckcat

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: July 31, 2009 05:06PM

haha that's because I increased the counter to 200 lol doh! It actually works. Maybe I need to prompt every mod 20 or something

Fixed it now, I reduced the counter from 200 to 20 and you can confirm if you want the loop to carry on or not. Sorry about that

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]



Edited 1 time(s). Last edit at 08/01/2009 04:42AM by Gareth Heyes.

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: kangax
Date: August 02, 2009 12:30AM

Speaking of `valueOf`:

var o = { valueOf: function(){ return 1; } };
o + 1; // expected: 2, actual: [object Object]1

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: kangax
Date: August 02, 2009 12:37AM

Also, `Error` doesn't seem to be implemented; and it's impossible to extend built-in prototypes:

Array.prototype.sum = function(){
var result = 0, i = this.length;
while (i--) result += this;
return result;
};
[1,2,3].sum(); // expected: 6, actual: TypeError

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 03, 2009 09:36AM

@kangax

Ok you can now prototype everything :D and use valueOf, toString
How is this possible? Well I create a new window context for each execution, which allows you to define prototypes inside the new window whilst leaving the parent window intact.

Thanks!

Anyone who is using JSReg now (I only know of sirdarckcat and Achim), you'll have to define your own error handler using the debug objects. This is because the exception is no longer caught as it is in a iframe. Also the eval function no longer returns the result as the window might not be ready, you need to define a callback in the debug objects. The two samples are below:-

//Error handling
function errorHandler(e, parser) {
			if (e.description) {
					var msg = '';
					if (e.description) {
						msg += 'Description:' + e.description + '\n';
					}
					if(e.msg) {
						msg += 'Msg:'+e.msg+'\n';
					}
					if (e.line) {
						msg += 'Line:' + e.line+'\n';
					}
					if (parser.debugObjects.parseTree) {
						parser.debugObjects.parseTree(e.parseTree);
					}					
					if (parser.debugObjects.errorLog) {
						parser.debugObjects.errorLog(msg);
					} else {
						alert(msg);
					}
				} else {
					if (parser.debugObjects.errorLog) {
						parser.debugObjects.errorLog(e);
					} else {
						alert(e);
					}
				}			
		}
parser.setDebugObjects({errorHandler: function(e) {
  errorHandler(e, parser);
}
});

//getting the result:-
parser.setDebugObjects({
result: function(code){
										document.getElementById('result').value = 'type:'+typeof code+'\n'+code;
}
});

View the HTML file to see all the options

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: kangax
Date: August 04, 2009 03:12PM

Found another parser bug :)

x=4/2/2/*/*/; // expected: 1, actual: SyntaxError

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 04, 2009 03:47PM

@kangax

That is sweet, I dunno how you find them :)
I'll fix soon nice one!

Update......
Ok fixed! thx :)

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]



Edited 1 time(s). Last edit at 08/04/2009 04:11PM by Gareth Heyes.

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 05, 2009 08:48AM

I pwnd myself doh!

x=(1,[][[]+'sort'])()
x[[[]+'eval']]('alert("PWND! "+document.domain)')

This is a problem with the array detection, I've fixed it now temporary. But I'll need to do something in future to stop it

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 06, 2009 10:44AM

Right, I've rewritten how JSReg handles arrays. I now identify only when the [] is used as a property identifier and not an array. The RegExp works like this:-

squaresStart = new RegExp('(?:[\\)\\]]|'+variable.source+'|'+regexpObj.source+'|'+strings.source+')'),

So any matches that find a ")", string, variable, regexp followed by a "[" it will be rewritten as a object property. E.g.:-

'a'[0] // will be rewritten
(1)['__parent__'] // will be rewritten
/a/[1] // will be rewritten

x=[1,2,3]//will NOT be rewritten
([1,2,3,[1]])//will NOT be rewritten

This way I can make a fake lookbehind assertion without affecting the other matches as the arrays are left as they are. I've not benchmarked these regexps but they should be a lot faster now as I'm matching much less.

Here is an example on how to attack it:-
Й=1;
Й['__parent__']

Because I use a non alpha-num character as a variable you can get a reference to window. I plan to close this soon.

Update....
Fixed :)

Update2...
btw prototypes aren't working yet and the sandbox is still in the current window

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]



Edited 2 time(s). Last edit at 08/06/2009 11:46AM by Gareth Heyes.

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 07, 2009 07:07AM

JSReg now has scope :D BIG thanks to sirdarckcat who suggested using the JSReg constructor to apply scope to the iframe.

Here's how it works:-
//document.getElementById('JSReg_Environment') is a iframe
var parser = JSReg(document.getElementById('JSReg_Environment'));

OR
//creates a iframe ghost
var parser = JSReg('ghost');

This makes any changes to the Object prototypes only affect the scope sent. You can have more than one object running at the same time and they won't affect each other as long as you provide two different scopes.

Update...
Fixed the code slightly, you now have to use a callback because the ghost window has to finish loading before the object is returned:-
JSReg('ghost',function(JSReg_instance) {
JSReg_instance.eval("1+1");
});

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]



Edited 1 time(s). Last edit at 08/07/2009 10:24AM by Gareth Heyes.

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 08, 2009 05:39AM

Hacked myself again =)

[] properties are a weak area in JSReg

hack to window:-
''
['__parent__']

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: sirdarckcat
Date: August 08, 2009 06:24AM

why that works?
you are not using globals.gp anymore?

--edit--
do you need to do the <script src="url+jsreg_environment"? why not sending the code directly via toString of a function()? Since now I have to wait untill a network request is finished to businessinfo before actually executing anything and thats too slow =(.

Also, the asynchronous stuff is not very cool haha, why do you need the callback for exactly?


Also, something is missing here I think hah:
function error() {
throw {
description: d,
msg: msg,
};
}

this are arguments d? msg? or are defined somewhere else

Also, I recomend doing the iframe width:1 height:1 with frameborder:0 and position:absolute with top-100 and left-100 to avoid it being flashing in the bottom of the page :P display none/visiblity hidden caused problems on IE iirc

--------------------------------
http://sirdarckcat.blogspot.com/ http://www.sirdarckcat.net/ http://foro.elhacker.net/ http://twitter.com/sirdarckcat



Edited 4 time(s). Last edit at 08/08/2009 10:43AM by sirdarckcat.

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 08, 2009 04:49PM

Yeah but now I'm not detecting arrays and sqaures is a new regexp.

Quote

do you need to do the <script src="url+jsreg_environment"? why not sending the code directly via toString of a function()? Since now I have to wait untill a network request is finished to businessinfo before actually executing anything and thats too slow =(.

Yeah in my tests it was the only way of making the prototypes private, if you know of a better way please let me know and I'll implement it.

I'll make the frame 1px and fix the exception sorry it was a quick fix :)

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: sirdarckcat
Date: August 09, 2009 02:25AM

You can try with:

document.write("<script>(function(JSRE){window.JSReg_Environment=JSRE})("+JSReg_Environment+");</script>");
document.close();

:D

--------------------------------
http://sirdarckcat.blogspot.com/ http://www.sirdarckcat.net/ http://foro.elhacker.net/ http://twitter.com/sirdarckcat

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 11, 2009 10:39AM

Ok I've updated the sandbox, it now uses a dynamic iframe and injects the correct code without the need for a callback. Ghosts are just not possible cross browser :( I managed to get the iframes working correctly but the only way I could get it to work in every browser is to delete the iframe after the eval has been run. In some browsers it would work before the eval and in different places but I couldn't fix all the problems in every browser :(

If you can find a way let me know, or prototype the JSREg object and I'll add it

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: sirdarckcat
Date: August 11, 2009 09:18PM

this code works in Chrome, Firefox, Safari, IE and Opera:

var iframe=document.createElement('iframe');
document.body.appendChild(iframe);
iframe.contentWindow.document.write("<script>top.safeEval=function(x){return eval(x+'')}</script>");
iframe.contentWindow.document.close();
iframe.parentNode.removeChild(iframe);
safeEval('String.prototype.toUpperCase=function(){return "lol";};"smile".toUpperCase();')+'!='+"smile".toUpperCase();

feel free to replace safeEval's argument with.. "location=123" for example, to check which window is the owner.

What's not working?

Greetings!!

--------------------------------
http://sirdarckcat.blogspot.com/ http://www.sirdarckcat.net/ http://foro.elhacker.net/ http://twitter.com/sirdarckcat



Edited 2 time(s). Last edit at 08/11/2009 10:30PM by sirdarckcat.

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: sirdarckcat
Date: August 13, 2009 10:14PM

dude, I just hacked your sandbox!

x={'i hack':'you'}['__parent__']

x is window, ftw!

--------------------------------
http://sirdarckcat.blogspot.com/ http://www.sirdarckcat.net/ http://foro.elhacker.net/ http://twitter.com/sirdarckcat

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: August 14, 2009 02:37AM

Nice one!!

I bet it is because of the lookbehind problem :( The object is being eaten by Object RegExp and the square regexp thinks it starts with [

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: September 03, 2009 10:16AM

After many, many, many, many, many RegExps and code rewrites I've finally implemented something that protects against this attack. It is unbelievably hard to detect the object properties using []. I've settled for a cheat, basically I look for a closing "]" which is preceded with a dangerous string or object/function, I have to protect against strings which are harmful like __parent__.

When this detection occurs I add a element to the end of the array or object property, I do it to both because it's extremely difficult for me to detect an array or object property without doing multiple scans or crazy RegExps. So now it's pretty safe against object based attacks like these but has a major downside of modifying the contents of many arrays. At the moment when a Arrays toString method is called I remove the ending property, however the length will be altered as well. I have to fix this yet.

So I almost gave up but hopefully I'll be able to work round these and correct the array length and prevent access to this special property.

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: kangax
Date: September 03, 2009 01:41PM

We need a way to create AST from string of javascript code - all with javascript. I was just thinking about something like that recently. Too bad I'm not much familiar with compilers/parsers.

If we have AST of a program, then there is obviously no ambiguity between property accessors and array initializers. Otherwise, there will probably always be a way to fool sandbox parser.

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: September 03, 2009 03:18PM

@kangax

Yeah, I've found the most difficult part is the [] syntax. Other stuff isn't that bad although still tricky. Another thing that makes it difficult is the amount of code you can place between [] and () this makes it hard to define a simplified version of the language without crippling it and making it slow. I still think it's possible and I'm sure I can improve it

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: October 23, 2009 01:36PM

I must be honest I almost give up as either I'm not good enough to match the [] or javascript isn't capable of matching the combinations using regexps. But I found a alternative solution that should protect against all __parent__ related attacks with object properties.

JSReg now converts all [] as object properties and if you require Arrays you need to use the Array(1,2,3) constructor. The reason I've done this is the amount of problems I've had with [] I never felt confident that all holes would be closed but this way I'm almost sure.

Here is a sample:-
x=Array(1,2,3);//This is how to create arrays in JSReg [] for arrays not supported
alert(x[2])//x[] are only used for object properties

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: kangax
Date: October 23, 2009 02:58PM

@Gareth

So to create array with 1 numeric value, say — [2] — one would need to do something like — `var a = Array(); a[0] = 2`?

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: Gareth Heyes
Date: October 23, 2009 03:31PM

@kangax

Yep this is a good point. I could change it but this is how the major browsers currently implement it.

x=Array(1);
x

So x is a blank array without the value of "1". I think I should leave it as that is how it is supposed to work. I guess in the JSReg documentation I could point this out or FAQ or whatever.

When using more than one element you can do it like this:-
x=Array(1,2,3);
x.length == 3

------------------------------------------------------------------------------------------------------------
"People who say it cannot be done should not interrupt those who are doing it.";
labs : [www.businessinfo.co.uk]
blog : [www.thespanner.co.uk]
Hackvertor : [hackvertor.co.uk]



Edited 1 time(s). Last edit at 10/23/2009 03:32PM by Gareth Heyes.

Options: ReplyQuote
Re: JSReg sandbox challenge
Posted by: sirdarckcat
Date: October 25, 2009 08:15AM

Haha! well.. I am sad that it wasnt possible to go around the [] issue.. but in any case! I agree.. since well.. it's a problem difficult to tackle.

Anyway,

var x=[2];

is = to:

Array(0,2).slice(-1)

is not a perfect solution but well.... c'est la vie.. hehe :)

Greetz!!

--------------------------------
http://sirdarckcat.blogspot.com/ http://www.sirdarckcat.net/ http://foro.elhacker.net/ http://twitter.com/sirdarckcat



Edited 1 time(s). Last edit at 10/25/2009 08:23AM by sirdarckcat.

Options: ReplyQuote
Pages: Previous1234567891011...LastNext
Current Page: 4 of 13


Sorry, only registered users may post in this forum.