<?xml version="1.0" encoding="utf-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
    <channel>
        <title>ssong_14.log</title>
        <link>https://velog.io/</link>
        <description>안녕하세요</description>
        <lastBuildDate>Sun, 19 Nov 2023 06:58:21 GMT</lastBuildDate>
        <docs>https://validator.w3.org/feed/docs/rss2.html</docs>
        <generator>https://github.com/jpmonette/feed</generator>
        <image>
            <title>ssong_14.log</title>
            <url>https://images.velog.io/images/ssong_14/profile/4758af2f-27d7-459e-9342-c8ff774b1315/social.jpeg</url>
            <link>https://velog.io/</link>
        </image>
        <copyright>Copyright (C) 2019. ssong_14.log. All rights reserved.</copyright>
        <atom:link href="https://v2.velog.io/rss/ssong_14" rel="self" type="application/rss+xml"/>
        <item>
            <title><![CDATA[기수 정렬(Radix sort)]]></title>
            <link>https://velog.io/@ssong_14/%EA%B8%B0%EC%88%98-%EC%A0%95%EB%A0%ACRadix-sort</link>
            <guid>https://velog.io/@ssong_14/%EA%B8%B0%EC%88%98-%EC%A0%95%EB%A0%ACRadix-sort</guid>
            <pubDate>Sun, 19 Nov 2023 06:58:21 GMT</pubDate>
            <description><![CDATA[<p>각 자리별로 정렬 1의자리부터 n의 자리까지 </p>
<pre><code class="language-c">int main() {
    int nums[6];
    for (int i = 0; i &lt; 6; ++i) scanf(&quot;%d&quot;, &amp;nums[i]);
    int count_a[10] = { 0, };
    int count_b[10] = { 0, };
    for (int i = 0; i &lt; 6; i++)
    {
        count_a[nums[i] / 10]++;
        count_b[nums[i] % 10]++;
    }
    int rank_a[10] = { 0, };
    int rank_b[10] = { 0, };
    rank_a[0] = count_a[0];
    rank_b[0] = count_b[0];
    for (int i = 1; i &lt; 10; i++)
    {
        rank_a[i] = rank_a[i - 1] + count_a[i];
        rank_b[i] = rank_b[i - 1] + count_b[i];
    }

    int sorted_arr[6] = { 0, };
    for (int i = 5; i &gt;= 0; i--) sorted_arr[--rank_b[nums[i] % 10]] = nums[i];
    for (int i = 5; i &gt;= 0; i--) nums[--rank_a[sorted_arr[i] / 10]] = sorted_arr[i];
    for (int i = 0; i &lt; 6; ++i) printf(&quot;%d &quot;, nums[i]);
    return 0;
}</code></pre>
]]></description>
        </item>
        <item>
            <title><![CDATA[SFTP 연동하기]]></title>
            <link>https://velog.io/@ssong_14/SFTP-%EC%97%B0%EB%8F%99%ED%95%98%EA%B8%B0</link>
            <guid>https://velog.io/@ssong_14/SFTP-%EC%97%B0%EB%8F%99%ED%95%98%EA%B8%B0</guid>
            <pubDate>Tue, 17 Oct 2023 02:11:29 GMT</pubDate>
            <description><![CDATA[<h2 id="ftp-vs-sftp">FTP vs SFTP</h2>
<p>SFTP연동을 하기에 앞서 FTP와 SFTP의 차이점에 대해 이해하고 있어야 합니다. 이 둘의 차이점을 아신다면 다음 chapter로 넘어가셔도 됩니다. </p>
<table>
<thead>
<tr>
<th>FTP(port:21)</th>
<th>SFTP(port:22)</th>
</tr>
</thead>
<tbody><tr>
<td>파라미터로 패스워드를 전송</td>
<td>파라미터로 패스워드 전송이 불가능</td>
</tr>
</tbody></table>
<p>보안적인 측면에 있어서 SFTP 방식이 기존의 인증키를 공유함으로써 패스워드의 노출을 막고 인증된 사용자만이 ftp 서버에 로그인할 수 있습니다.</p>
<h2 id="sftp-접속방식">SFTP 접속방식</h2>
<p> SFTP는 SSH 방식으로 서버 간에 암호화된 데이터를 주고 받습니다. SFTP는 기본적으로 22번 포트를 사용하므로 방화벽을 열어주어야 합니다. 
방화벽 open 및 포트 Listen과 동시에 Local Server와 접속할 FTP 서버간 인증키를 발급해서 공유해 놓습니다. </p>
<h2 id="ssh-key">SSH key</h2>
<ol>
<li><p>인증키가 있는경우 발급할 필요없이 해당 키를 전송하면 됩니다.
 a. 인증키 확인</p>
<pre><code class="language-bash"> ls -al ~/.ssh</code></pre>
</li>
</ol>
<ol start="2">
<li><p>인증키가 없는경우 새롭게 생성하여 해당 키를 전송해야 합니다. 
 a. 인증키 생성</p>
<pre><code class="language-bash"> ssh-keygen -t rsa</code></pre>
</li>
<li><p>생성(확인)한 ssh key를 서버에 전송합니다.</p>
<pre><code class="language-bash">ssh-copy-id -i ~/.ssh/id_rsa.pub &lt;서버 IP&gt;</code></pre>
</li>
</ol>
<p>이제 FTP서버(DST 서버)에 ssh로 password 없이 접속이 가능합니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/1fa2840d-cdd5-4a66-91c0-e1b9cbbda86d/image.png" alt=""></p>
<h2 id="script로-sftp-연동하기">Script로 SFTP 연동하기</h2>
<p>이제 ssh 키 인증을 통해 자유롭게 접근이 가능한 SFTP 서버를 PUT 형태로 파일을 전송해 보도록 하겠습니다. </p>
<ol>
<li>수집 서버에서 스크립트를 작성합니다.</li>
</ol>
<pre><code class="language-bash">#!/bin/bash
# SFTP 서버로 보낼 파일에 포함된 날짜형식을 정의합니다.
IB_DATE=`date -d &quot;-1 days&quot; +%Y%m%d`
# 서버를 작성합니다.
IP=192.168.1.13
# put할 대상 파일의 위치를 작성합니다.
SRC_DIR=“/var/log“
# sftp 서버의 저장 경로를 설정합니다. 해당 경로는 자동으로 발급된 앞 내용의 경로를 작성해야 합니다.
DST_DIR=“/192.168.1.35/22“
# 루트 계정을 원하시지 않는다면 sftp 그룹과 계정을 만들어 DST_DIR 경로에 접근권한을 부여하면 됩니다.
sftp root@$IP &lt;&lt; End-Of-Session
lcd $SRC_DIR
cd $DST_DIR
put maillog-${IB_DATE}*
bye
End-Of-Session</code></pre>
<pre><code class="language-bash">sh 스크립트명</code></pre>
<ol>
<li>이제 cron에 등록하여 매일 수집할 수 있도록 자동화합니다.</li>
</ol>
<pre><code class="language-bash">crontab -e</code></pre>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/9af6930f-a11e-44b5-9dec-4c9d95dcc46b/image.png" alt=""></p>
<p>각 *는 띄어쓰기로 구분하며 왼쪽부터 주기적으로 실행할 분 / 시 / 일 / 월 / 요일(일요일(0) ~ 토요일(6)) 을 의미합니다. 이후 실행할 커맨드라인을 입력하면 crontab에 등록할 수 있습니다.</p>
<p>감사합니다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[SNMP 프로토콜]]></title>
            <link>https://velog.io/@ssong_14/SNMP-%ED%94%84%EB%A1%9C%ED%86%A0%EC%BD%9C</link>
            <guid>https://velog.io/@ssong_14/SNMP-%ED%94%84%EB%A1%9C%ED%86%A0%EC%BD%9C</guid>
            <pubDate>Fri, 22 Sep 2023 05:47:58 GMT</pubDate>
            <description><![CDATA[<h3 id="snmp란">SNMP란?</h3>
<p> SNMP(Simple Network Management Protocol)는 UDP/IP를 사용하여 이더넷 연결을 통해 네트워크 관리 작업을 수행하는 응용 계층 프로토콜입니다.</p>
<p> 주로 네트워크 장치 또는 시스템(라우터, 스위치, 서버, 프린터)의 <strong>상태 및 성능 정보</strong>를 모니터링하고 구성하는데 사용됩니다.</p>
<h3 id="snmp-oidobject-identifier">SNMP OID(Object Identifier)</h3>
<ol>
<li>MIB는 OID를 통해 개체를 식별하고 설명합니다.</li>
</ol>
<blockquote>
<p>MIB(Management Information Base)란?
 SNMP에서 수집한 시스템(또는 장치)의 상태 및 성능 정보를 정의하는 DB 또는 계층적인 트리 구조를 말합니다.
 따라서 각 정보들을 구분하기 위해 SNMP OID라는 값을 사용합니다.</p>
</blockquote>
<ol>
<li>SNMP 메시지 : 서버와 해당 장비(시스템)간의 통신을 위해 메시지를 사용합니다.</li>
</ol>
<ul>
<li>GET : 서버가 시스템에 특정 OID 정보를 요청합니다.</li>
<li>SET : 서버가 에이전트에게 특정 OID 값을 설정하도록 요청합니다.</li>
</ul>
<p>일반적으로 사용되는 버전은 SNMPv2이고, SNMPv3는 보안 및 인증 기능을 향상시킨 버전으로 비밀번호와 같은 보안기능을 제공합니다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[TLS(SSL) 암호화 프로토콜]]></title>
            <link>https://velog.io/@ssong_14/TLS</link>
            <guid>https://velog.io/@ssong_14/TLS</guid>
            <pubDate>Fri, 22 Sep 2023 03:27:08 GMT</pubDate>
            <description><![CDATA[<h1 id="tls">TLS</h1>
<h3 id="tls전송-계층-보안">TLS(전송 계층 보안)</h3>
<ul>
<li>인터넷 상의 커뮤니케이션을 위한 개인 정보와 데이터 보안을 용이하게 하기 위해 설계된 보안 프로토콜입니다.</li>
<li>웹 브라우저와 서버간의 커뮤니케이션을 암호화하며 이메일, 메시지 등 다른 커뮤니케이션을 암호화 하는데도 사용합니다.</li>
<li>우리가 흔히 알고있는 HTTPS 프로토콜은 HTTP + TLS 암호화 입니다.</li>
</ul>
<aside>
💡 가장 최신버전은 2018년 발표된 1.3 입니다.

</aside>

<h3 id="tls와-ssl의-차이점">TLS와 SSL의 차이점</h3>
<p>TLS는 SSL 3.1버전으로 개발한 암호화 프로토콜이지만 Netscape와 연관이 없음을 명시하기 위해 프로토콜 명칭이 변경되었습니다. </p>
<blockquote>
<p>SSL은 뭔가요?
1995년 Netscape에서 처음 개발된 암호화 기반 인터넷 프로토콜입니다.
작동방법</p>
</blockquote>
<ol>
<li>웹을 통해 전송되는 데이터를 암호화합니다.</li>
<li>핸드셰이크라는 인증 프로세스를 시작하여 두 장치를 확인합니다.</li>
<li>무결성을 검증합니다.
1996년 이후로 업데이트 되지 않으며 현재는 더 이상 사용되지 않는 것으로 간주된다고 합니다.<blockquote>
</blockquote>
</li>
</ol>
<aside>
❗ 3-way-handshake와 다른 개념입니다. TLS(SSL) 핸드셰이크는 TCP 핸드셰이크를 통해 TCP 연결이 열린 후 발생합니다.

</aside>

<h3 id="tls의-요소">TLS의 요소</h3>
<p>SSL과 마찬가지로 TLS 프로토콜은 다음 세가지의 요소를 만족합니다.</p>
<ol>
<li>암호화 : 제 3자로부터 전송되는 데이터를 숨깁니다.</li>
<li>인증 : 정보를 교환하는 당사자가 요청된 당사자임을 보장합니다. </li>
<li>무결성 : 데이터가 위조되거나 변조되지 않았는지 확인합니다.</li>
</ol>
<h3 id="tls-핸드셰이크">TLS 핸드셰이크</h3>
<pre><code class="language-markdown"> 1) 클라이언트가 서버에게 접속 요청을 보냅니다. (클라이언트가 지원하는 TSL 버전, 암호화 알고리즘 목록, 랜덤 바이트 문자열)

 2) 서버는 클라이언트가 지원하는 알고리즘 중 하나를 선택하고 서버의 SSL 인증서, 서버에서 생성한 무작위 바이트 문자열을 메시지에 담아 클라이언트로 보냅니다.

 3) 서버의 메시지를 받은 클라이언트는 서버가 인증서에 명시된 서버인지, 실제 해당 도메인의 소유자인지를 확인합니다. 클라이언트는 서버의 SSL 인증서를 CA(발행 기관) 리스트를 통해 검증합니다. 이 과정에서 클라이언트에 내장된 CA 공개키를 이용해서 인증서를 복호화합니다. 또한 SSL 인증서를 통해 서버의 공개키를 알아냅니다.

 4) 클라이언트가 PMS(Pre-Master-Secret)를 생성합니다. 

- PMS = 서버의 무작위 문자열 + 클라이언트의 무작위 문자열

 5) 3에서 알아낸 서버의 공개키를 가지고 PMS를 암호화하여 서버에 보냅니다. 

 6) 서버는 클라이언트로부터 받은 PMS를 서버의 개인키로 복호화합니다. 이제 둘다 PMS를 들고있습다.

 7) 서버와 클라이언트는 PMS를 MS(Master Secret) 값으로 다시 Session Key로 만듭니다. [PMS → MS → Session Key]

 8) 서버와 클라이언트는 세션키로 암호화된 ‘완료’ 메시지를 서로 보냅니다. 

 9) TSL 핸드셰이킹 완료!</code></pre>
]]></description>
        </item>
        <item>
            <title><![CDATA[Syslog Priority]]></title>
            <link>https://velog.io/@ssong_14/Syslog-Priority</link>
            <guid>https://velog.io/@ssong_14/Syslog-Priority</guid>
            <pubDate>Fri, 22 Sep 2023 01:17:04 GMT</pubDate>
            <description><![CDATA[<h2 id="syslog-priority">Syslog Priority</h2>
<p>Syslog Priority는 번역하자면, 시스템 로그 우선순위입니다.</p>
<blockquote>
<p>Q. syslog는 무엇인가요?
 syslog는 일반적으로 UNIX 및 UNIX 계열 운영 체제에서 로그 메시지를 수집하고 전송하기 위한 표준화된 프로토콜 서비스입니다.
 syslog 프로토콜은 UDP 또는 TCP를 사용하여 로그 메시지를 전송할 수 있으며 메시지는 주로 텍스트 형식으로 전송됩니다.</p>
</blockquote>
<p><strong>그렇다면 로그 수집 서버에서 무작위로 수집한 로그 중 어떤 로그가 중요한지 어떻게 알 수 있을까요?</strong></p>
<p>syslog priority는 이러한 로그를 발생시키는 유형(Facility)와 심각도(Severity)에 따라 등급(Priority)이 나뉘게 됩니다. </p>
<p>아래 표에서 </p>
<blockquote>
<p>우선순위 값(Priority) = 장비 X 8 + 심각도</p>
</blockquote>
<table>
<thead>
<tr>
<th>심각도 ➡️</th>
<th>0 (Emergency)</th>
<th>1 (Alert)</th>
<th>2 (Critical)</th>
<th>3 (Error)</th>
<th>4 (Warning)</th>
<th>5 (Notice)</th>
<th>6 (Info)</th>
<th>7 (Debug)</th>
</tr>
</thead>
<tbody><tr>
<td>유형⬇️</td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
<tr>
<td>kernel(0)</td>
<td>0</td>
<td>1</td>
<td>2</td>
<td>3</td>
<td>4</td>
<td>5</td>
<td>6</td>
<td>7</td>
</tr>
<tr>
<td>user(1)</td>
<td>8</td>
<td>9</td>
<td>10</td>
<td>11</td>
<td>12</td>
<td>13</td>
<td>14</td>
<td>15</td>
</tr>
<tr>
<td>mail(2)</td>
<td>16</td>
<td>17</td>
<td>18</td>
<td>19</td>
<td>20</td>
<td>21</td>
<td>22</td>
<td>23</td>
</tr>
<tr>
<td>system(3)</td>
<td>24</td>
<td>25</td>
<td>26</td>
<td>27</td>
<td>28</td>
<td>29</td>
<td>30</td>
<td>31</td>
</tr>
<tr>
<td>security(4)</td>
<td>32</td>
<td>33</td>
<td>34</td>
<td>35</td>
<td>36</td>
<td>37</td>
<td>38</td>
<td>39</td>
</tr>
<tr>
<td>syslog(5)</td>
<td>40</td>
<td>41</td>
<td>42</td>
<td>43</td>
<td>44</td>
<td>45</td>
<td>46</td>
<td>47</td>
</tr>
<tr>
<td>lpd(6)</td>
<td>48</td>
<td>49</td>
<td>50</td>
<td>51</td>
<td>52</td>
<td>53</td>
<td>54</td>
<td>55</td>
</tr>
<tr>
<td>nntp(7)</td>
<td>56</td>
<td>57</td>
<td>58</td>
<td>59</td>
<td>60</td>
<td>61</td>
<td>62</td>
<td>63</td>
</tr>
<tr>
<td>uucp(8)</td>
<td>64</td>
<td>65</td>
<td>66</td>
<td>67</td>
<td>68</td>
<td>69</td>
<td>70</td>
<td>71</td>
</tr>
<tr>
<td>시간(9)</td>
<td>7272</td>
<td>73</td>
<td>74</td>
<td>75</td>
<td>76</td>
<td>77</td>
<td>78</td>
<td>79</td>
</tr>
<tr>
<td>보안(10)</td>
<td>8080</td>
<td>81</td>
<td>82</td>
<td>83</td>
<td>84</td>
<td>85</td>
<td>86</td>
<td>87</td>
</tr>
<tr>
<td>FTPD(11)</td>
<td>88</td>
<td>89</td>
<td>90</td>
<td>91</td>
<td>92</td>
<td>93</td>
<td>94</td>
<td>95</td>
</tr>
<tr>
<td>ntpd(12)</td>
<td>96</td>
<td>97</td>
<td>98</td>
<td>99</td>
<td>100</td>
<td>101</td>
<td>102</td>
<td>103</td>
</tr>
<tr>
<td>로그 감사(13)</td>
<td>104</td>
<td>105</td>
<td>106</td>
<td>107</td>
<td>108</td>
<td>109</td>
<td>110</td>
<td>111</td>
</tr>
<tr>
<td>로그 경고(14)</td>
<td>112</td>
<td>113</td>
<td>114</td>
<td>115</td>
<td>116</td>
<td>117</td>
<td>118</td>
<td>119</td>
</tr>
<tr>
<td>시계(15)</td>
<td>120</td>
<td>121</td>
<td>122</td>
<td>123</td>
<td>124</td>
<td>125</td>
<td>126</td>
<td>127</td>
</tr>
<tr>
<td>로컬0(16)</td>
<td>128</td>
<td>129</td>
<td>130</td>
<td>131</td>
<td>132</td>
<td>133</td>
<td>134</td>
<td>135</td>
</tr>
<tr>
<td>로컬1(17)</td>
<td>136</td>
<td>137</td>
<td>138</td>
<td>139</td>
<td>140</td>
<td>141</td>
<td>142</td>
<td>143</td>
</tr>
<tr>
<td>…</td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
<td></td>
</tr>
</tbody></table>
<p>표에 나타나 있지 않은 값이라면 /(나누기) 8 한 몫이 유형 나머지가 심각도입니다. </p>
<p>예를 들어 로그 우선순위가 &lt;165&gt; 라면 로컬 4의 Notice 정보입니다.</p>
<blockquote>
<p>출처 : <a href="https://datatracker.ietf.org/doc/html/rfc5424#section-6.2.1">https://datatracker.ietf.org/doc/html/rfc5424#section-6.2.1</a></p>
</blockquote>
]]></description>
        </item>
        <item>
            <title><![CDATA[iptables와 firewalld]]></title>
            <link>https://velog.io/@ssong_14/iptables%EC%99%80-firewalld</link>
            <guid>https://velog.io/@ssong_14/iptables%EC%99%80-firewalld</guid>
            <pubDate>Tue, 19 Sep 2023 03:22:18 GMT</pubDate>
            <description><![CDATA[<blockquote>
<p>출처 : <a href="https://www.lesstif.com/ws/%EB%B0%94%EC%81%9C-%EA%B0%9C%EB%B0%9C%EC%9E%90%EB%A5%BC-%EC%9C%84%ED%95%9C-%EC%9B%B9-%EC%84%9C%EB%B9%84%EC%8A%A4-%EB%B3%B4%EC%95%88-43843784.html">https://www.lesstif.com/ws/%EB%B0%94%EC%81%9C-%EA%B0%9C%EB%B0%9C%EC%9E%90%EB%A5%BC-%EC%9C%84%ED%95%9C-%EC%9B%B9-%EC%84%9C%EB%B9%84%EC%8A%A4-%EB%B3%B4%EC%95%88-43843784.html</a></p>
</blockquote>
<h2 id="iptables">iptables</h2>
<ul>
<li>Linux의 전통적인 방화벽 관리 도구로 규칙을 직접 설정하고 관리해야한다.</li>
</ul>
<h2 id="firewalld">firewalld</h2>
<ul>
<li>iptables 기반의 방화벽 관리 도구이다.</li>
</ul>
<h2 id="firewalld의-장점">firewalld의 장점</h2>
<ul>
<li>동적으로 규칙 변경이 가능하다. <ul>
<li>firewall-cmd : 동적으로 규칙 변경이 가능하지만 일시적이다.</li>
<li>firewall-cmd --permanent : 즉시 적용이 불가하지만 재부팅시 정책이 지속된다. </li>
</ul>
</li>
<li>서비스 및 포트 기반의 설정을 제공한다. 이를테면 iptables는 포트 및 프로토콜에 대한 규칙을 일일이 작성해주어야 하지만, firewalld는 특정 서비스 포트를 이름으로 허용 또는 차단할 수 있다. <ul>
<li><code>$ sudo firewall-cmd --permanent --zone=webserver --add-service=http</code>이런식으로 말이다.</li>
</ul>
</li>
<li>GUI를 제공한다.
linux firewall-config
<img src="https://velog.velcdn.com/images/ssong_14/post/30e776fa-af1d-49d6-87f9-83e49e957c70/image.png" alt=""><blockquote>
<p>출처 : 레드햇</p>
</blockquote>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[Private Registry Service 구축 [Nexus/ MINIO](2)]]></title>
            <link>https://velog.io/@ssong_14/Private-Registry-Service-%EA%B5%AC%EC%B6%95-2</link>
            <guid>https://velog.io/@ssong_14/Private-Registry-Service-%EA%B5%AC%EC%B6%95-2</guid>
            <pubDate>Tue, 25 Jul 2023 19:11:44 GMT</pubDate>
            <description><![CDATA[<h2 id="nexus">Nexus</h2>
<p><strong>소프트웨어 저장소 관리 시스템</strong></p>
<ul>
<li>주로 소프트웨어 개발에서 사용되는 의존성 관리, 라이브러리 관리, 릴리스 관리, 빌드 자동화 등을 수행할때 사용하며 중앙 저장소 역할을 합니다.</li>
<li>프로젝트에서 필요로 하는 라이브러리 버전을 관리하여 프로젝트의 안정성과 일관성을 유지할 수 있습니다.</li>
</ul>
<p>이번 주제는 넥서스를 proxy서버로 이용해 s3 object storage를 사용하는 방법입니다.
주로 docker image 파일을 pull/cache 용도로 사용할 것입니다.</p>
<h2 id="minio">MINIO</h2>
<p><strong>Object Storage Server</strong>
S3와 호환되는 API를 제공하여 기존 S3를 사용하여 app과 통합할 수 있습니다. 객체 스토리지를 이용해 대규모 데이터를 저장하고 관리하는데 사용되며, 대부분의 클라우드 서비스에서 데이터를 저장하는 기본 형태입니다.</p>
<ol>
<li>FS 방식<ul>
<li>백엔드 파일 시스템을 사용합니다.</li>
</ul>
</li>
<li>ES(Erase Coding) 방식<ul>
<li>데이터를 EC 코덱 알고리즘으로 인코딩하여 복제를 통해 각기 다른 disk로 할당합니다.</li>
</ul>
</li>
</ol>
<h3 id="vagrantfile">Vagrantfile</h3>
<pre><code>VAGRANTFILE_API_VERSION = &quot;2&quot;
    Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|
    config.vm.box = &quot;ubuntu/focal64&quot;
    config.vm.provider &quot;virtualbox&quot; do |vb|
            vb.memory = 2048
    end
    if Vagrant.has_plugin?(&quot;vagrant-vbguest&quot;)
        config.vbguest.auto_update = false
    end
    config.vm.synced_folder &quot;.&quot;, &quot;/vagrant&quot;, type: &quot;rsync&quot;, rsync__exclude: [&quot;.git/&quot;]
    config.vm.provision &quot;shell&quot;, inline: &lt;&lt;-SHELL
        export DEBIAN_FRONTEND=noninteractive
        sudo apt -y update
        sudo apt install -y ca-certificates curl gnupg libnss-mdns
        sudo install -m 0755 -d /etc/apt/keyrings
        curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
        sudo chmod a+r /etc/apt/keyrings/docker.gpg
        echo &quot;deb [arch=&quot;$(dpkg --print-architecture)&quot; signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu &quot;$(. /etc/os-release &amp;&amp; echo &quot;$VERSION_CODENAME&quot;)&quot; stable&quot; | sudo tee /etc/apt/sources.list.d/docker.list &gt; /dev/null
        sudo apt -y update
        sudo apt install -y docker-ce docker-ce-cli containerd.io docker-compose-plugin
        sudo usermod -aG docker vagrant
    SHELL
    config.vm.define &quot;ceph&quot;, primary: true do |ceph|
        ceph.vm.hostname = &quot;ceph.local&quot;
        ceph.vm.network &quot;private_network&quot;, ip: &quot;192.168.34.101&quot;
        ceph.vm.disk :disk, size:&quot;25GB&quot;, name: &quot;extra1&quot;
        ceph.vm.disk :disk, size:&quot;25GB&quot;, name: &quot;extra2&quot;
    end
    config.vm.define &quot;registry&quot;, primary: true do |registry|
        registry.vm.hostname = &quot;registry.local&quot;
        registry.vm.network &quot;private_network&quot;, ip: &quot;192.168.34.102&quot;
    end
    config.vm.define &quot;node&quot;, primary: true do |node|
        node.vm.hostname = &quot;node.local&quot;
        node.vm.network &quot;private_network&quot;, ip: &quot;192.168.34.103&quot;
    end
    config.vm.define &quot;minio&quot;, primary: true do |minio|
        minio.vm.hostname = &quot;minio.local&quot;
        minio.vm.network &quot;private_network&quot;, ip: &quot;192.168.34.104&quot;
        minio.vm.disk :disk, size:&quot;25GB&quot;, name: &quot;extra1&quot;
        minio.vm.disk :disk, size:&quot;25GB&quot;, name: &quot;extra2&quot;
    end
    config.vm.define &quot;harbor&quot;, primary: true do |harbor|
        harbor.vm.hostname = &quot;harbor.local&quot;
        harbor.vm.network &quot;private_network&quot;, ip: &quot;192.168.34.105&quot;
    end
end
</code></pre><p>이전 Ceph의 Vagrantfile과 다르게 Ceph 환경과 minio 환경에 각각 vm disk를 추가로 입력하여 Extra disk 를 만들겠습니다. 
이 Extra disk를 volume으로 minio에 붙여(mount) 사용할 예정입니다.</p>
<h3 id="1-minio-가상-머신-실행-및-접속">1. MINIO 가상 머신 실행 및 접속</h3>
<pre><code class="language-bash">$ VAGRANT_EXPERIMENTAL=&quot;disks&quot; vagrant up minio
$ vagrant ssh minio</code></pre>
<blockquote>
<p>해당 명령어는 linux기반 명령어로 window powershell일 경우 아래 명령어로 입력해야 합나다. 혹은 git bash terminal을 이용하면 사용할 수 있습니다.</p>
</blockquote>
<pre><code class="language-bash">windows
$ $env:VAGRANT_EXPERIMENTAL=&quot;disks&quot;
$ vagrant up minio
$ vagrant ssh minio</code></pre>
<h3 id="2-추가한-disk-format">2. 추가한 disk format</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/b0215bd1-5a74-436c-b74d-dcbccb3eea00/image.png" alt=""></p>
<blockquote>
<p>mount 이전에는 MOUNTPOINT가 보이지 않습니다.</p>
</blockquote>
<pre><code class="language-bash">$ sudo mkfs.xfs /dev/sdc -L DISK1
$ sudo mkfs.xfs /dev/sdd -L DISK2</code></pre>
<p>mkfx.xfs는 xfs 파일 시스템을 생성하는 명령어 입니다. Label 명을 붙여 포맷시킵니다.
xfs는 ext4에 비해 대용량 데이터 처리와 큰 파일일 경우 우수한 성능을 가집니다.</p>
<h3 id="3-mount">3. mount</h3>
<p>xfs 파일 시스템으로 포맷한 disk를 mount합니다.</p>
<pre><code>mount할 directory
$ sudo mkdir -p /mnt/disk1 /mnt/disk2

$ sudo vi /etc/fstab

$ sudo mount -a</code></pre><p><img src="https://velog.velcdn.com/images/ssong_14/post/c9b05169-6fca-4772-9b0a-01fb81e16593/image.png" alt=""></p>
<h3 id="4-minio-실행하기">4. MINIO 실행하기</h3>
<pre><code class="language-bash">$ docker run -d --name minio -p 9000-9001:9000-9001 \
              -v /mnt/disk1:/data1 \
              -v /mnt/disk2:/data2 \
              -e MINIO_ROOT_USER=&lt;id&gt; \
              -e MINIO_ROOT_PASSWORD=&lt;password&gt;\
              minio/minio \
              server /data1 /data2 --console-address &quot;:9001&quot;</code></pre>
<blockquote>
<p>한줄에 작성하되 비밀번호는 너무 쉬우면 안됩니다. (최소 문자 3개가 필요)</p>
</blockquote>
<h3 id="5-포트포워딩">5. 포트포워딩</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/d37dd4cb-b002-42ca-8a65-efc2999564ab/image.png" alt=""></p>
<h3 id="6-buckets-추가">6. Buckets 추가</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/b3a3ddb4-9bf4-4288-a5e7-52721e9045df/image.png" alt=""></p>
<h3 id="7-registry-실행-및-접속">7. registry 실행 및 접속</h3>
<pre><code class="language-bash">$ vagrant up registry
$ vagrant ssh registry</code></pre>
<h3 id="8-volume-생성-및-실행docker-compose">8. volume 생성 및 실행(docker-compose)</h3>
<pre><code class="language-bash">$ docker volume create nexus-data</code></pre>
<h4 id="docker-composeyml">docker-compose.yml</h4>
<pre><code class="language-yml">services:
  nexus:
    image: sonatype/nexus3
    container_name: nexus
    environment:
      - INSTALL4J_ADD_VM_PARAMS=-Xms1024m -Xmx1024m -XX:MaxDirectMemorySize=512m -Djava.util.prefs.userRoot=/nexus-data/javaprefs
    ports:
      - 8081:8081
      - 5000-5001:5000
    volumes:
      - nexus-data:/nexus-data
volumes:
  nexus-data:
    external: true
</code></pre>
<blockquote>
<p>-Djava.util.prefs.userRoot=/nexus-data/javaprefs
해당 내용은 지속적인 error log를 출력합니다.
<a href="https://community.sonatype.com/t/problem-afer-upgrading-to-3-42-0-could-not-lock-user-prefs/9568">https://community.sonatype.com/t/problem-afer-upgrading-to-3-42-0-could-not-lock-user-prefs/9568</a> </p>
</blockquote>
<h3 id="9-포트포워딩">9. 포트포워딩</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/24ec55a0-85d3-495b-a42e-e5800c489866/image.png" alt=""></p>
<h3 id="10-자동-설정된-비밀번호-찾기">10. 자동 설정된 비밀번호 찾기</h3>
<pre><code>#id = admin
docker exec -it nexus cat /nexus-data/admin.password</code></pre><h3 id="11-nexus3의-blob-store를-minio에서-사용하도록-설정하기">11. nexus3의 blob store를 MINIO에서 사용하도록 설정하기</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/7768c2fe-543e-4729-95c8-1287a266162f/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/56b962e7-1655-4ea8-b17d-53b0295df9db/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/58105ad0-f0d4-459c-a6d8-34e7c37aef8b/image.png" alt=""></p>
<blockquote>
<p>type : S3
Access Key ID : minio에서 설정한 계정
Secret access key : minio에서 설정한 비밀번호
Endpoint URL : minio ipaddress</p>
</blockquote>
<h3 id="12-docker-repository-추가하기">12. docker repository 추가하기</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/2261e3be-1110-4568-a0eb-b24d7c558754/image.png" alt=""></p>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/824b1f46-3eeb-42b6-8e9a-5ce657c0bdac/image.png" alt=""></p>
<ol>
<li><p>docker(proxy)
외부 docker-hub에서 image 파일을 가져오기 위한 프록시서버입니다.
설정은 아래와 같습니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/002ab51f-1a19-467f-837b-049ccf8fdf2f/image.png" alt=""></p>
</li>
<li><p>docker(hosted)
proxy서버 이전에 cache 또는 host에 저장 및 접근하기 위한 서버입니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/5a38ebd9-d0a5-4dff-aa74-ff6e0deb08d3/image.png" alt=""></p>
</li>
<li><p>docker(group)
hosted 서버와 proxy 서버 등을 그루핑합니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/e116ab25-5b91-417e-b797-226735710595/image.png" alt=""></p>
</li>
</ol>
<p>member repository에 쌓인 순서대로 탐색을 합니다.</p>
<blockquote>
<p> 주의 : Allow anonymous docker pull을 체크해야 이미지를 가져오는데 nexus3 서버를 통합니다 아닐경우 docker-hub로 직접 갑니다..</p>
</blockquote>
<h3 id="13-realms-설정하기">13. Realms 설정하기</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/dcc1576b-c595-4795-afe3-708710d18f44/image.png" alt=""></p>
<p>docker login을 위한 bearer 토큰을 설정합니다.</p>
<h3 id="14-node-환경-실행">14. Node 환경 실행</h3>
<pre><code class="language-bash">$ vagrant up node
$ vagrant ssh node</code></pre>
<h3 id="15-node-daemonjson-수정">15. Node Daemon.json 수정</h3>
<pre><code class="language-json"># /etc/docker/daemon.json
{
  # nexus3가 돌고있는 registry 환경
  &quot;registry-mirrors&quot;: [&quot;http://192.168.34.102:5000&quot;],
  &quot;insecure-registries&quot;: [&quot;192.168.34.102:5000&quot;]
}</code></pre>
<h3 id="16-docker-image-pull-test">16. docker image pull test</h3>
<pre><code class="language-bash">$ docker pull ubunut:latest</code></pre>
<h3 id="17-실행-결과">17. 실행 결과</h3>
<ul>
<li>nexus
<img src="https://velog.velcdn.com/images/ssong_14/post/9a59bca6-9a84-4eee-b645-37aa034cbe0b/image.png" alt=""></li>
<li>MINIO
<img src="https://velog.velcdn.com/images/ssong_14/post/19f29d12-4ceb-47ed-9636-c670b53a96fd/image.png" alt=""></li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[Private Registry Service 구축 [Ceph] (1)]]></title>
            <link>https://velog.io/@ssong_14/Private-Registry-Service-%EA%B5%AC%EC%B6%95</link>
            <guid>https://velog.io/@ssong_14/Private-Registry-Service-%EA%B5%AC%EC%B6%95</guid>
            <pubDate>Tue, 25 Jul 2023 17:06:04 GMT</pubDate>
            <description><![CDATA[<h2 id="0-vagrantfile">0. Vagrantfile</h2>
<pre><code class="language-Vagrantfile">VAGRANTFILE_API_VERSION = &quot;2&quot;
    Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|
    config.vm.box = &quot;ubuntu/focal64&quot;
    config.vm.provider &quot;virtualbox&quot; do |vb|
            vb.memory = 2048
    end
    if Vagrant.has_plugin?(&quot;vagrant-vbguest&quot;)
        config.vbguest.auto_update = false
    end
    config.vm.synced_folder &quot;.&quot;, &quot;/vagrant&quot;, type: &quot;rsync&quot;, rsync__exclude: [&quot;.git/&quot;]
    config.vm.provision &quot;shell&quot;, inline: &lt;&lt;-SHELL
        export DEBIAN_FRONTEND=noninteractive
        sudo apt -y update
        sudo apt install -y ca-certificates curl gnupg libnss-mdns
        sudo install -m 0755 -d /etc/apt/keyrings
        curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
        sudo chmod a+r /etc/apt/keyrings/docker.gpg
        echo &quot;deb [arch=&quot;$(dpkg --print-architecture)&quot; signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu &quot;$(. /etc/os-release &amp;&amp; echo &quot;$VERSION_CODENAME&quot;)&quot; stable&quot; | sudo tee /etc/apt/sources.list.d/docker.list &gt; /dev/null
        sudo apt -y update
        sudo apt install -y docker-ce docker-ce-cli containerd.io docker-compose-plugin
        sudo usermod -aG docker vagrant
    SHELL
    config.vm.define &quot;ceph&quot;, primary: true do |ceph|
        ceph.vm.hostname = &quot;ceph.local&quot;
        ceph.vm.network &quot;private_network&quot;, ip: &quot;192.168.34.101&quot;
    end
    config.vm.define &quot;registry&quot;, primary: true do |registry|
        registry.vm.hostname = &quot;registry.local&quot;
        registry.vm.network &quot;private_network&quot;, ip: &quot;192.168.34.102&quot;
    end
    config.vm.define &quot;node&quot;, primary: true do |node|
        node.vm.hostname = &quot;node.local&quot;
        node.vm.network &quot;private_network&quot;, ip: &quot;192.168.34.103&quot;
    end
end
</code></pre>
<h2 id="1-ceph-storage">1. CEPH STORAGE</h2>
<ol>
<li>storage를 제공하는 서비스</li>
</ol>
<ul>
<li>File System 제공 (Remote File System / NFS)</li>
<li>Block 서비스 제공 (iSCSI) </li>
<li>Object Storage 제공 (S3)</li>
</ul>
<ol start="2">
<li>CEPH의 내부 구조
OSD Node: Object Storage Disk를 제공하는 디스크 노드 (SSD/HDD)<ul>
<li>Block 형태로 제공</li>
<li>MONs : Monitor 노드 </li>
<li>MGRs : Manager 노드</li>
<li>iSCSI-GW </li>
<li>Object Storage 형태로 제공</li>
<li>RADOS-GW</li>
<li>NFS나 SAT 파일 시스템 형태로 제공</li>
<li>MDS</li>
</ul>
</li>
<li>일반적으로 1개 이상의 마스터 노드(MON/MGR + GW)와 다수의 데이터 노드(OSD Node)들로 구성되어 있습니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/9b645d54-821e-4ed3-8ce1-349a71d734f6/image.png" alt=""><blockquote>
<p>출처 : Grepp</p>
</blockquote>
</li>
</ol>
<h2 id="2-ceph-모니터-구성">2. CEPH 모니터 구성</h2>
<blockquote>
<p>Docker Ceph/daemon image : 다중 호스트일 때 key value 형태의 데이터를 저장하려면 ETCD 서비스를 별도로 띄워야 합니다.</p>
</blockquote>
<h3 id="monitor-노드">Monitor 노드</h3>
<p><strong>(without KV STORE(암호화 FS))</strong></p>
<pre><code class="language-yml"># Docker-compose.yml
services:
  ceph-mon:
  # latest-mimic 이미지로 실행하지 않을 경우 에러가 발생할 수 있습니다.
    image: ceph/daemon:latest-mimic
    network_mode: host
    container_name: ceph-mon
    volumes:
      - /etc/ceph:/etc/ceph
      - /var/lib/ceph:/var/lib/ceph
    environment:
      - MON_IP=192.168.34.101
      - CEPH_PUBLIC_NETWORK=192.168.34.0/24
    command:
      mon</code></pre>
<blockquote>
<p>keyring issue : <a href="https://github.com/ceph/ceph-container/issues/1683">https://github.com/ceph/ceph-container/issues/1683</a></p>
</blockquote>
<h3 id="manager-노드관리-데몬">Manager 노드(관리 데몬)</h3>
<pre><code class="language-yml"># Docker-compose.yml
ceph-mgr:
    image: ceph/daemon:latest-mimic
    network_mode: host
    container_name: ceph-mgr
    volumes:
      - /etc/ceph:/etc/ceph
      - /var/lib/ceph:/var/lib/ceph
    command:
      mgr</code></pre>
<h3 id="osd-노드-배포">OSD 노드 배포</h3>
<pre><code class="language-yml">  ceph-osd:
    image: ceph/daemon:latest-mimic
    network_mode: host
    privileged: true
    container_name: ceph-osd
    volumes:
      - /etc/ceph:/etc/ceph
      - /var/lib/ceph:/var/lib/ceph
      - /dev:/dev
      - /run/udev:/run/udev
    environment:
    # sdc 디스크를 추가로 virtualbox에 생성
      - OSD_DEVICE=/dev/sdc
      - OSD_TYPE=disk
    command:
      osd</code></pre>
<h3 id="메타데이터-서버mds-배포">메타데이터 서버(mds) 배포</h3>
<p>FS형태로 제공하는 노드(NFS, CephFS 등)
<strong>DATA_POOL</strong> : mds 는 블럭 중 일부를 할당받아 CephFS로 만듭니다. 이때 사용할 data 파일 내용에 대한 정보를 DATA_POOL이라 합니다. </p>
<pre><code class="language-yml">  ceph-mds:
    image: ceph/daemon:latest-mimic
    network_mode: host
    volumes:
      - /var/lib/ceph:/var/lib/ceph
      - /etc/ceph:/etc/ceph
    environment:
      - CEPHFS_CREATE=1
    command:
      mds</code></pre>
<h3 id="ceph-dashboard-모듈-및-서비스-활성화">ceph dashboard 모듈 및 서비스 활성화</h3>
<pre><code> docker exec -it ceph-mgr ceph mgr module enable dashboard

 docker exec -it ceph-mgr ceph dashboard create-self-signed-cert

 docker exec -it ceph-mgr ceph mgr services
</code></pre><p> 실행 결과
 <img src="https://velog.velcdn.com/images/ssong_14/post/1e43bdf0-01a7-4533-81a7-8944a7397057/image.png" alt=""></p>
<h3 id="포트포워딩">포트포워딩</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/45bdd435-e712-4afb-83c9-bb189f03ae03/image.png" alt=""></p>
<h3 id="ceph-계정-생성">Ceph 계정 생성</h3>
<pre><code>docker exec -it ceph-mgr ceph dashboard set-login-credentials &lt;id&gt; &lt;pw&gt;</code></pre><h3 id="실행-결과">실행 결과</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/e2fb302b-6f2e-44fd-b001-42d3338c0531/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[Dockerfile 작성방법]]></title>
            <link>https://velog.io/@ssong_14/Dockerfile-%EC%9E%91%EC%84%B1%EB%B0%A9%EB%B2%95</link>
            <guid>https://velog.io/@ssong_14/Dockerfile-%EC%9E%91%EC%84%B1%EB%B0%A9%EB%B2%95</guid>
            <pubDate>Mon, 24 Jul 2023 21:36:03 GMT</pubDate>
            <description><![CDATA[<h2 id="from-구문">FROM 구문</h2>
<ul>
<li>기반 이미지를 지정합니다.</li>
</ul>
<pre><code class="language-Dockerfile"># FROM 이미지이름
# FROM 이미지이름:태그(버전)
# FROM 이미지이름@다이제스트
FROM ubuntu:20.04</code></pre>
<h2 id="maintainer-구문">MAINTAINER 구문</h2>
<ul>
<li>이미지의 제작자를 기록해둡니다.<pre><code># MAINTAINER 이름 이메일
MAINTAINER Kim hyunsong &lt;ssong_14@naver.com&gt;</code></pre></li>
</ul>
<h2 id="env-구문">ENV 구문</h2>
<pre><code># ENV 환경변수이름 값
# ENV 환경변수이름=값 
ENV PYTHON3 python3.6
</code></pre><h2 id="run-구문">RUN 구문</h2>
<p>컨테이너가 빌드할때 실행되는 구문입니다.
실행 결과는 새로운 레이어로 구성되며 컨테이너 환경을 구성하기 위한 명령을 실행합니다.</p>
<blockquote>
<p>레이어 이미지
레이어는 파일 시스템 및 환경 정보를 말합니다.
RUN 등의 실행 구문으로 컨테이너 파일 시스템이 변경될 때 새로운 레이어에 변경사항을 기록합니다. </p>
</blockquote>
<ul>
<li>기본<pre><code># RUN CMD
RUN apt-get install gcc g++</code></pre></li>
<li>EXEC 형식<pre><code># RUN [&quot;실행파일&quot;, &quot;매개변수1&quot;, &quot;매개변수2&quot;]
RUN [&quot;/bin/bash&quot;, &quot;-c&quot;, &quot;echo HelloWorld!&quot;]</code></pre></li>
</ul>
<h2 id="add-구문">ADD 구문</h2>
<p>호스트의 파일시스템 혹은 원격 URL에 있는 파일/디렉토리를 컨테이너 이미지로 복사합니다.</p>
<ul>
<li>컨테이너에 복사된 파일/디렉토리의 소유주 (UID/GID)는 0입니다</li>
<li>소스파일이 원격URL인 경우 파일 권한은 600 (소유자만 읽고 쓸 수 있음)입니다.</li>
<li>빌드 컨텍스트 상위로 접근이 불가합니다.</li>
<li>호스트 파일이 압축파일인 경우 이를 풀어서 디렉토리 형태로 처리합니다.</li>
<li>목적지가 없다면 recursive하게 새로 생성됩니다.</li>
</ul>
<pre><code># ADD 원본파일 목적디렉토리
ADD test1.py test2.py /data
# 디렉토리도 복사가 가능합니다. (단, Dockerfile이 있는 디렉토리의 하위 디렉토리에만 접근이 가능합니다.)
ADD ./source /data</code></pre><h2 id="copy">COPY</h2>
<ul>
<li>ADD와 유사하지만 압축파일도 그대로 복사하는 특징이 있습니다.</li>
<li>ADD는 호스트 또는 원격에서만 복사가 가능하지만 COPY는 다른 이미지로부터 파일을 가져올 수 있습니다. </li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[Docker 명령어 모음]]></title>
            <link>https://velog.io/@ssong_14/Docker-%EB%AA%85%EB%A0%B9%EC%96%B4-%EB%AA%A8%EC%9D%8C</link>
            <guid>https://velog.io/@ssong_14/Docker-%EB%AA%85%EB%A0%B9%EC%96%B4-%EB%AA%A8%EC%9D%8C</guid>
            <pubDate>Mon, 24 Jul 2023 21:05:54 GMT</pubDate>
            <description><![CDATA[<h2 id="docker의-라이프사이클">Docker의 라이프사이클</h2>
<ol>
<li>컨테이너 패키징 -&gt; 이미지를 생성한다</li>
<li>패키징된 이미지를 실행 -&gt; 컨테이너를 전개(실행)한다</li>
<li>컨테이너를 종료한다</li>
<li>종료된 컨테이너 환경을 보관한다.</li>
</ol>
<h2 id="기본-명령어">기본 명령어</h2>
<h3 id="1-이미지-생성">1. 이미지 생성</h3>
<pre><code># docker 빌드 (이미지 생성)
docker build</code></pre><h3 id="2-태그를-추가하여-이미지-구분하기">2. 태그를 추가하여 이미지 구분하기</h3>
<pre><code>docker build -t 사용자이름/이미지이름:버전태그
# docker build -t hs/nginx:1.9</code></pre><h3 id="3-특정-경로의-dockerfile로-이미지-생성하기">3. 특정 경로의 Dockerfile로 이미지 생성하기</h3>
<pre><code>docker build -f /경로/도커파일</code></pre><h3 id="4-특정-경로의-dockerfile로-특정-태그를-추가하여-생성23">4. 특정 경로의 Dockerfile로 특정 태그를 추가하여 생성(2+3)</h3>
<pre><code>docekr build -t hs/nginx -f ./config/Dockerfile_A</code></pre><h3 id="5-컨테이너-전개">5. 컨테이너 전개</h3>
<pre><code>docker run [run 옵션] 이미지이름 [컨테이너 실행 옵션]</code></pre><h3 id="6-컨테이너-일시-중지">6. 컨테이너 일시 중지</h3>
<pre><code>docker pause [컨테이너 ID]</code></pre><h3 id="7-컨테이너-시작">7. 컨테이너 시작</h3>
<pre><code>docker start [컨테이너 ID]</code></pre><h3 id="8-전개중인-컨테이너-확인-실행-중지-포함">8. 전개중인 컨테이너 확인 (실행, 중지 포함)</h3>
<pre><code>docker ps
# -a 옵션으로 중지된 모든 컨테이너를 볼 수 있음</code></pre><h3 id="9-컨테이너-종료">9. 컨테이너 종료</h3>
<pre><code># 기본 SIGTERM을 컨테이너 내의 프로세스에 전달한다.
docker stop [컨테이너 ID]
# 강제 종료 (SIGKILL)
docker kill [컨테이너 ID]</code></pre><h3 id="10-종료된-컨테이너-환경을-이미지로-보관">10. 종료된 컨테이너 환경을 이미지로 보관</h3>
<pre><code>docker commit [컨테이너ID] [새로운 태그]
# 실행 중 변경된 사항이 저장되며 저장된 결과에 태그를 주어 새로운 이름을 부여할 수 있다.</code></pre>]]></description>
        </item>
        <item>
            <title><![CDATA[Vagrant, Ansible-playbook으로 docker-registry 실행하기]]></title>
            <link>https://velog.io/@ssong_14/Vagrant-Ansible-playbook%EC%9C%BC%EB%A1%9C-docker-registry-%EC%8B%A4%ED%96%89%ED%95%98%EA%B8%B0</link>
            <guid>https://velog.io/@ssong_14/Vagrant-Ansible-playbook%EC%9C%BC%EB%A1%9C-docker-registry-%EC%8B%A4%ED%96%89%ED%95%98%EA%B8%B0</guid>
            <pubDate>Mon, 24 Jul 2023 10:18:42 GMT</pubDate>
            <description><![CDATA[<h2 id="vagrant">Vagrant</h2>
<p>가상 머신을 프로비저닝하고 구성하는 툴입니다.</p>
<h2 id="ansible">Ansible</h2>
<p>구성 관리 자동화 도구입니다.
특징으로는 인벤토리가 있는데 Ansible은 관리 대상 시스템의 목록을 포함하는 인벤토리 파일을 사용합니다.
원격 시스템의 hostname 또는 IP주소를 정의하고 호스트 그룹을 구성하거나 변수를 설정하는데 사용됩니다.</p>
<h2 id="vagrantfile">Vagrantfile</h2>
<pre><code class="language-Vagrant">VAGRANTFILE_API_VERSION = &quot;2&quot;

Vagrant.configure(VAGRANTFILE_API_VERSION) do |config|
    config.vm.box = &quot;ubuntu/focal64&quot;
    config.vm.hostname = &quot;ansible.local&quot;
    config.vm.provider &quot;virutalbox&quot; do |vb|
        vb.memory = 1024
    end

    if Vagrant.has_plugin?(&quot;vagrant-vbguest&quot;)
        config.vbguest.auto_update = false
    end

    config.vm.network &quot;private_network&quot;, ip: &quot;192.168.{xx}.{xx}&quot;
    config.vm.synced_folder &quot;.&quot;, &quot;/vagrant&quot;, type: &quot;rsync&quot;, rsync__exclude: [&quot;.git/&quot;]

    config.vm.provision &quot;shell&quot;, inline: &lt;&lt;-SHELL
        export DEBIAN_FRONTEND=noninteractive
        sudo apt -y update
        sudo apt install -y ca-certificates apt-transport-https
        sudo apt install -y software-properties-common curl
        sudo apt install -y python3-pip python-is-python3
        sudo add-apt-repository --yes --update ppa:ansible/ansible
        sudo apt install -y ansible
        sudo pip3 install docker
      SHELL
    end
</code></pre>
<p>위 설정을 통해 가상 머신의 os를 ubuntu LTS로 받아 실행할 수 있습니다.</p>
<pre><code class="language-bash">vagrant up

vagrant ssh</code></pre>
<p>을 통해 실행 및 접속합니다.</p>
<p>이제 가상머신의 자동화가 완료되었습니다.</p>
<p>ansible을 이용하여 docker를 설치하고 실행하는 스크립트를 작성해 보겠습니다.</p>
<br>
ansible 은 인벤토리의 구조에 해당하는 내용을 스크립트로 작성합니다.

<p>다음은 ansible 환경을 구성하기 위한 디렉토리 구조입니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/d0ddcef3-42f6-45af-a8ad-5e5886ac80cc/image.png" alt=""></p>
<h2 id="siteyml">site.yml</h2>
<pre><code class="language-yml">---
- hosts: localhost
  become: yes
  roles:
          - docker-install
          - docker-registry
~                              </code></pre>
<h2 id="mainyml-dir--playbookrolesdocker-installtasks">main.yml (dir : ~/playbook/roles/docker-install/tasks)</h2>
<pre><code class="language-yml">- name: Add Docker GPG apt Key
  apt_key:
         url: https://download.docker.com/linux/ubuntu/gpg
         state: present

- name: Add Docker Repository
  apt_repository:
          repo: deb https://download.docker.com/linux/ubuntu focal stable
          state: present

- name: Update apt and install docker-ce
  apt:
          name: docker-ce
          state: latest
          update_cache: true
~                             </code></pre>
<h2 id="mainyml-dir--playbookrolesdocker-registrytasks">main.yml (dir : ~/playbook/roles/docker-registry/tasks)</h2>
<pre><code class="language-yml"># 1. Pull Docker Registry Image
- name: Pull Docker Registry image
  community.docker.docker_image:
          name: registry
          source: pull
# 2. Create directory for registry config.yml
- name: Create directory for registry config.yml
  file:
          path: /etc/docker/registry/
          state: directory

# 3. Configure registry config.yml
- name: Configure registry config.yml
  copy:
          dest: /etc/docker/registry/config.yml
          content:
                  proxy:
                          remoteurl: https://registry-1.docker.io


# 4. Create docker registry container
- name: Create docker registry container
  community.docker.docker_container:
          name: registry
          image: registry
          detach: true
          recreate: true
          restart_policy: unless-stopped
          mounts:
                - type: bind
                  source: /etc/docker/registry/
                  target: /etc/registry/
          ports:
                - 5000:5000
          state: started
# 5. Update daemon.json

- name: Update daemon.json
  copy:
          dest: /etc/docker/daemon.json
          content: |
                  {
                          &quot;registry-mirrors&quot;: [&quot;http://localhost:5000&quot;]
                  }

# 6. Restart docker daemon
- name: Restart docker daemon
  systemd:
          name: docker
          state: restarted</code></pre>
<p>이제 마지막으로 ansible playbook으로 docker를 설치 및 docker-registry를 실행합니다.</p>
<pre><code class="language-bash">ansible-playbook site.yml</code></pre>
<h2 id="실행-결과">실행 결과</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/3ead394a-a368-48d1-a0ac-8ec607c7050c/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[네트워크 테스트베드 구축]]></title>
            <link>https://velog.io/@ssong_14/%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC-%ED%85%8C%EC%8A%A4%ED%8A%B8%EB%B2%A0%EB%93%9C-%EA%B5%AC%EC%B6%95</link>
            <guid>https://velog.io/@ssong_14/%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC-%ED%85%8C%EC%8A%A4%ED%8A%B8%EB%B2%A0%EB%93%9C-%EA%B5%AC%EC%B6%95</guid>
            <pubDate>Sun, 09 Jul 2023 07:04:12 GMT</pubDate>
            <description><![CDATA[<h2 id="테스트-베드">테스트 베드</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/88e7a4e9-806d-44be-bcb2-837613bf9b71/image.png" alt="">
출처 : K-Digital-Training: 리눅스 시스템 및 커널 전문가 과정 / 리눅스 네트워크 및 보안 설정</p>
<h2 id="0-virtualbox-nat-네트워크-설정">0. Virtualbox NAT 네트워크 설정</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/016a2474-c697-4747-bb0c-b3afbcf9f284/image.png" alt=""></p>
<ol>
<li><p>NET_NAT : 사설 IP 내부망 1</p>
</li>
<li><p>NET_NAT : 사설 IP 내부망 2</p>
</li>
<li><p>NET_NAT: 외부 접속을 위한 NAT</p>
</li>
</ol>
<h2 id="1-가상머신을-고정-ip-주소로-설정">1. 가상머신을 고정 IP 주소로 설정</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/1f80be6b-0a45-46c3-abec-9764b20e309e/image.png" alt=""></p>
<blockquote>
<p>IP 주소 확인 및 유동 IP를 고정 IP 주소로 변환하기 위해 리눅스는 /etc/netplan/00-installer-config.yaml 파일에서 변경이 가능합니다.</p>
</blockquote>
<h2 id="2-vm1-vm2의-라우팅-테이블-확인게이트웨이-변경-확인">2. vm1, vm2의 라우팅 테이블 확인(게이트웨이 변경 확인)</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/7282fd8e-33f5-4dba-b6bb-5dde7ed0a3b8/image.png" alt=""></p>
<blockquote>
<p>vm3 과 vm4도 동일하게 진행하면 됩니다.</p>
</blockquote>
<h2 id="3-vm5-네트워크-설정">3. vm5 네트워크 설정</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/98951f10-0a46-4d25-b1cc-8ba496d0a430/image.png" alt="">
vm5는 vm1-2의 게이트웨이이자 vm3-4의 게이트웨이이면서 외부로 접속하기위한 nat 도 필요합니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/8ddd881e-b6fe-40dc-aea5-2bdee1735cbf/image.png" alt=""></p>
<h2 id="4-최종-ip-및-route-형태">4. 최종 IP 및 route 형태</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/04d00610-4888-4b92-b169-dd5f263a436d/image.png" alt=""></p>
<h2 id="테스트">테스트</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/6c3e74b0-2934-4aaa-81ed-5e4aa1bd5a88/image.png" alt=""></p>
<p>이제 사설 내부망까지 통신이 가능합니다.
하지만 외부와 통신하기 위해서는 어느 ip로 들어와야하는지 외부에서는 알지 못합니다.
따라서 게이트 웨이 패킷 포워딩을 설정해주어야 합니다.</p>
<h2 id="5-패킷-포워딩">5. 패킷 포워딩</h2>
<p>vi /etc/sysctl.conf 파일을 수정해야 합니다.</p>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/8a27dcd2-995f-45fd-9b09-aa2851ba2054/image.png" alt=""></p>
]]></description>
        </item>
        <item>
            <title><![CDATA[Dump kernel page table Trouble Shooting]]></title>
            <link>https://velog.io/@ssong_14/Dump-kernel-page-table-Trouble-Shooting</link>
            <guid>https://velog.io/@ssong_14/Dump-kernel-page-table-Trouble-Shooting</guid>
            <pubDate>Mon, 12 Jun 2023 12:08:45 GMT</pubDate>
            <description><![CDATA[<h1 id="dump-kernel-page-table-trouble-shooting">Dump kernel page table Trouble Shooting</h1>
<p>가급적 su로 빌드 및 실행하시길 바랍니다.</p>
<p>아래 문제들은 각자의 환경마다 다를 수 있습니다.</p>
<p>trouble </p>
<ol>
<li>arch/x86/Makefile:142: CONFIG_X86_X32 enabled but no binutils support<ul>
<li>CONFIG_X86_X32 옵션은 x32 ABI를 지원하기 위한 옵션이며, 해당 옵션이 활성화되었지만 binutils 패키지에서 x32를 지원하지 않아서 발생하는 오류입니다.</li>
</ul>
</li>
<li>make -j5<ul>
<li>병렬로 make 명령을 실행할 때 발생할 수 있는 오류입니다.</li>
<li><code>echo $?</code> 를 입력하여 값이 있는 경우 build가 제대로 되지 않은 경우입니다.</li>
</ul>
</li>
<li>make 시 permission denied로 빌드가 중단될 수 있습니다.</li>
<li>make[1]: *** No rule to make target &#39;debian/canonical-revoked-certs.pem&#39;, needed by &#39;certs/x509_revocation_list&#39;.  Stop.<ul>
<li>시스템 폐기 키 관련 문제입니다. </li>
<li><a href="https://askubuntu.com/questions/1362455/i-am-installing-kernel-in-my-ubuntu-but-getting-an-error">https://askubuntu.com/questions/1362455/i-am-installing-kernel-in-my-ubuntu-but-getting-an-error</a></li>
</ul>
</li>
</ol>
<p>solution</p>
<ol>
<li><p>make menuconfig에서 X32 ABI의 지원을 비활성화 해주어야 합니다.</p>
<ul>
<li><p>make menuconfig 에서 x32를 검색하시면 위치가 binary emulation 인 symbol이 하나 있습니다. <del>잘 못찾겠어서 그냥 검색(/)했습니다. (잘 안보이네요..)</del>
<img src="https://velog.velcdn.com/images/ssong_14/post/372017c4-37fd-43ab-a3c5-8e8fd3aa39ad/image.png" alt=""></p>
</li>
<li><p>해당 옵션(x32 ABI for 64-bit mode)을 비활성화 해줍니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/b2f1ebc3-e27f-4be7-919e-3cf415f0b959/image.png" alt=""></p>
</li>
</ul>
</li>
</ol>
<ol start="2">
<li><p>make clean 후 재시도 하셔야 합니다. (저는그냥 make로 돌렸습니다. 대략 1시간 정도 build 하는 것 같네요 ( 제 cpu 기준입니다 .))</p>
</li>
<li><p>su나 sudo 로 실행하시기 바랍니다.</p>
</li>
<li><p>리눅스 소스 디렉터리에서 <code>scripts/config --disable SYSTEM_REVOCATION_KEYS</code> 를 실행하시면 폐기 키를 제거할 수 있습니다.</p>
<ol>
<li>해당 폐기 키 비활성화 후 make 시 key 입력을 받는데 그냥 enter로 넘어가시면 됩니다.</li>
</ol>
</li>
</ol>
]]></description>
        </item>
        <item>
            <title><![CDATA[병합 정렬]]></title>
            <link>https://velog.io/@ssong_14/%EB%B3%91%ED%95%A9-%EC%A0%95%EB%A0%AC</link>
            <guid>https://velog.io/@ssong_14/%EB%B3%91%ED%95%A9-%EC%A0%95%EB%A0%AC</guid>
            <pubDate>Sun, 11 Jun 2023 03:46:11 GMT</pubDate>
            <description><![CDATA[<pre><code class="language-c">#include &lt;stdio.h&gt;
#include &lt;stdlib.h&gt;

/*
병합정렬
1. 나눌수 있는 최소한의 배열로 쪼갠다
2. 합친다.
*/
void merge(int left, int mid, int right, int arr[])
{
  // 0, 1, 3
  int n1 = mid - left + 1;
  int n2 = right - mid;
  int left_arr[n1];
  int right_arr[n2];

  // 배열 초기화

  for (int i = 0; i &lt; n1; i++)
  {
    // i : 0 ~ 1까지
    // left + i : 0 ~ 1 까지
    left_arr[i] = arr[left + i];
  }
  for (int i = 0; i &lt; n2; i++)
  {
    // i : 0~ 1 까지
    // mid + 1 + i : 2 ~ 3 까지
    right_arr[i] = arr[mid + 1 + i];
  }
  // 갱신할 배열 인덱스 idx
  // 좌측 배열 인덱스 p
  // 우측 배열 인덱스 q
  int idx=left, p =0, q = 0;
  while (p &lt; n1 &amp;&amp; q &lt; n2)
  {
    if (left_arr[p] &lt;= right_arr[q])
    {
      arr[idx++] = left_arr[p++];
    }
    else
    {
      arr[idx++] = right_arr[q++];
    }
  }

  while (p &lt; n1)
  {
    arr[idx++] = left_arr[p++];
  }
  while(q &lt; n2)
  {
    arr[idx++] = right_arr[q++];
  }

}







void merge_sort(int left, int right, int arr[])
{


  if (left &lt; right)
  {
    int mid = (left + right) / 2;
    merge_sort(left, mid, arr); // 0, 3 -&gt; 0, 1 -&gt; 
    merge_sort(mid + 1, right, arr); // 4, 7 -&gt; 5, 7 -&gt; 6, 7
    merge(left, mid, right, arr);

    for (int i =0; i &lt;8; i++)
    {
      printf(&quot;%d &quot;, arr[i]);
    }
    printf(&quot;\n&quot;);
  }
  return;


}


int main(void)
{
  int arr[8] = {3, 21, 5, 9, 2, 64, 17, 24}; 

  merge_sort(0, 7, arr);


  return 0;
}</code></pre>
]]></description>
        </item>
        <item>
            <title><![CDATA[Linux Container & Kubernetes]]></title>
            <link>https://velog.io/@ssong_14/Linux-Container-Kubernetes</link>
            <guid>https://velog.io/@ssong_14/Linux-Container-Kubernetes</guid>
            <pubDate>Tue, 30 May 2023 22:12:15 GMT</pubDate>
            <description><![CDATA[<blockquote>
<p>출처 레드햇</p>
</blockquote>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/6fd83cf6-942b-409e-a082-87de8102f5a8/image.png" alt=""></p>
<h2 id="리눅스-컨테이너">리눅스 컨테이너</h2>
<p>격리된 환경에서 실행되는 프로세스로 호스트머신의 운영체제와 커널은 공유하지만, 파일 시스템, 네트워크, 사용자ID 등의 자원은 격리되어 있습니다. 이러한 격리는 다른 컨테이너 또는 호스트 시스템에서 실행되는 프로세스에 영향을 미치지 않도록 합니다.</p>
<p>컨테이너 이미지를 사용하여 애플리케이션의 배포와 관리를 쉽게 할 수 있습니다.</p>
<h2 id="컨테이너-오케스트레이션-시스템">컨테이너 오케스트레이션 시스템</h2>
<p>여러 대의 컴퓨터에 걸쳐 컨테이너화된 애플리케이션을 배치하고, 확장하고, 관리하는 시스템입니다. 컨테이너 오케스트레이션 시스템에는 Kubernetes, Docker Swarm, Apache Mesos 등이 있습니다. 이들 시스템은 컨테이너 배포, 자동 확장, 자동 복구, 서비스 디스커버리 등의 기능을 제공하며, 클라우드 환경에서 사용되는 것이 일반적입니다.</p>
<h2 id="docker">Docker</h2>
<p>리눅스 컨테이너의 대표적인 플랫폼으로 컨테이너 이미지를 쉽게 빌드하고 배포할 수 있습니다.</p>
<p>애플리케이션을 격리된 컨테이너라는 유닛으로 패키징하고 배포할 수 있습니다. </p>
<p>Docker의 핵심 개념은 이미지, 컨테이너, 레지스트리입니다. </p>
<ul>
<li><p>이미지 : Docker 컨테이너를 실행하는데  필요한 모든 파일, 코드, 라이브러리, 의존성을 포함하는 패키지입니다. </p>
</li>
<li><p>컨테이너 : 이미지를 기반으로 생성되는 실행 가능한 인스턴스 입니다. </p>
</li>
<li><p>레지스트리 : 이미지를 저장하고 공유할 수 있는 저장소입니다.</p>
</li>
<li><p>호스트 시스템과는 독립적으로 배포할 수 있습니다.</p>
</li>
</ul>
<h2 id="도커-설치시-swap-메모리를-비활성화-하는-이유">도커 설치시 swap 메모리를 비활성화 하는 이유</h2>
<p>Docker는 독립적인 프로세스로 실행되며 이러한 독립성을 유지하기 위해서는 컨테이너가 호스트 시스템의 리소스를 직접 사용하지 않도록 해야합니다.</p>
<p>또한 Docker에서 swap 메모리를 사용하기 되면 컨테이너의 동작이 느려지거나 컨테이너가 중단될 수 있으며, 호스트 시스템의 성능 저하와 같은 부작용이 발생할 수 있습니다. </p>
<ul>
<li><p>swap 비활성화</p>
<blockquote>
<p>모든 스왑을 비활성화</p>
<p><code>sudo swapoff -a</code></p>
<p>/etc/fsatab 파일에서 swap.img를 사용하는 라인을 주석처리함</p>
<p><code>sudo sed -i &#39;/swap.img/s/^/#/&#39; /etc/fstab</code></p>
</blockquote>
</li>
</ul>
<h2 id="cgroup">cgroup</h2>
<p>프로세스 그룹을 관리하는 커널 기능</p>
<p>프로세스 그룹에 리소스 제한을 적용하고, 프로세스 그룹에 대한 계측 및 통제를 합니다.</p>
<p>cpu, 메모리, I/O, 네트워크 등의 리소스에서 제한을 할 수 있습니다.</p>
<h2 id="docker-데몬">Docker 데몬</h2>
<p>컨테이너의 생성, 관리, 실행을 담당하는 Docker의 백그라운드 프로그램</p>
<p>호스트와 컨테이너 간의 네트워크 통신을 관리하며, 이미지 빌드와 레지스트리 간의 통신을 담당합니다.</p>
<p>Docker를 사용하기 위해서는 Docker 데몬을 실행해야합니다.</p>
<p>daemon.json 설정</p>
<pre><code>{
  // cgroup 드라이버, systemd를 사용하도록 설정
  &quot;exec-opts&quot;: [&quot;native.cgroupdriver=systemd&quot;],
  // 로그 파일의 형식
  &quot;log-driver&quot;: &quot;json-file&quot;,
  // 로그 파일의 크기
  &quot;log-opts&quot;: {
    &quot;max-size&quot;: &quot;100m&quot;
  },
  // 저장 드라이버
  &quot;storage-driver&quot;: &quot;overlay2&quot;
}    </code></pre><blockquote>
<p>overlay2 :  파일 시스템 레이어를 효율적으로 관리하기 위해 메타데이터와 데이터를 분리하여 저장</p>
</blockquote>
<h2 id="docker-compose">docker-compose</h2>
<p>하나의 명령어로 전체 애플리케이션을 빌드, 시작, 중지, 제거할 수 있으며 각 컨테이너의 로그를 볼 수 있습니다. </p>
<h2 id="kubernetes">Kubernetes</h2>
<p>컨테이너화된 애플리케이션을 자동으로 배포, 확장 및 관리하기 위한 오픈소스 플랫폼</p>
<p>대규모 컨테이너 환경에서 원활한 배포, 확장, 관리를 위한 다양한 기능을 제공합니다.</p>
<p>쿠버네티스는 클러스터를 구성하며, 클러스터에는 여러개의 노드가 있습니다. </p>
<p>각 노드는 컨테이너를 실행하는 호스트입니다. </p>
<p>쿠버네티스의 역할 : 노드간 로드 밸런싱, 스케줄링, 자원할당, 상태 모니터링, 자가 치유 등을 담당한다.</p>
<blockquote>
<p>쿠버네티스 클러스터</p>
<p>여러 대의 서버를 하나의 시스템으로 관리하는 것</p>
<p>컴퓨터(서버) == 클러스터 노드</p>
<p>각 노드는 마스터 노드에 의해 관리, 마스터 노드는 클러스터 전체를 제어하는 제어 플레인 컴포넌트와 클러스터 상태를 유지하는 스토리지 및 API 서버 등의 컴포넌트로 구</p>
</blockquote>
<h2 id="쿠버네티스-pod">쿠버네티스 Pod</h2>
<p>하나 이상의 컨테이너를 포함하는 가장 작은 배포 단위입니다.</p>
<p>Pod는 고유한 IP주소를 가지며 Pod내의 컨테이너는 동일한 인터페이스와 파일 시스템을 공유합니다.</p>
<p><a href="https://www.redhat.com/ko/topics/containers/what-is-kubernetes-pod">https://www.redhat.com/ko/topics/containers/what-is-kubernetes-pod</a></p>
<h2 id="br_netfilter">br_netfilter</h2>
<p>linux 커널의 모듈중 하나로 네트워크 브릿지와 관련된 네트워크 패킷 필터링을 수행합니다.</p>
<p>네트워크 연결을 관리하고 iptables 및 ip6tables에서 사용되는 필터링 규칙을 적용하여 네트워크 보안을 강화합니다.</p>
<p>쿠버네티스 설치를 위해 필요한 모듈 설정 파일에 작성합니다.</p>
<pre><code>sudo vi /etc/modules-load.d/k8s.conf</code></pre><pre><code>br_netfilter</code></pre><h2 id="kubelet-kubeadm-kubectl">kubelet, kubeadm, kubectl</h2>
<p><code>kubelet</code>, <code>kubeadm</code>, <code>kubectl</code>은 쿠버네티스를 설치, 관리 및 제어하는 데 필요한 세 가지 도구입니다.</p>
<ul>
<li><code>kubelet</code>: 클러스터 노드에서 실행되는 쿠버네티스 에이전트로서, 컨테이너를 관리하고 클러스터 내부와 통신하는 데 사용됩니다.</li>
<li><code>kubeadm</code>: 쿠버네티스 클러스터를 부트스트래핑(초기화)하는 데 사용되는 도구로, 클러스터 구성 요소를 설치하고 구성하며, 마스터 노드를 초기화하는 데 사용됩니다.</li>
<li><code>kubectl</code>: 쿠버네티스 클러스터를 제어하기 위한 커맨드라인 도구로, 클러스터 내부의 오브젝트를 생성, 수정, 삭제 및 관리하는 데 사용됩니다.</li>
</ul>
<p>이 세 가지 도구를 함께 사용하여 쿠버네티스 클러스터를 구성하고 관리할 수 있습니다.</p>
<h2 id="cni">CNI</h2>
<p>CNI(CNI-Container Network Interface)는 Kubernetes 클러스터 내에서 Pod 간의 통신을 위한 네트워크 모델을 제공하는 인터페이스입니다. CNI는 Kubernetes에서 적용 가능한 네트워크 드라이버 플러그인을 사용하여 다양한 방식으로 구성 가능합니다.</p>
<p>CNI는 컨테이너 오케스트레이션 시스템에서 다양한 네트워크 솔루션들을 통합하여 사용 가능하도록 해주며, 그 중 대표적인 솔루션으로는 Calico, Flannel, Weave Net 등이 있습니다. CNI를 사용하면 Kubernetes에서는 각 Pod가 고유한 IP 주소를 가지며, Pod 간에는 가상 네트워크를 통해 통신합니다.</p>
<h2 id="calico">Calico</h2>
<p>Calico는 쿠버네티스 클러스터 내에서 네트워크 정책을 구현하는 데 사용되는 오픈소스 소프트웨어입니다. Calico는 라우팅, 로드 밸런싱 및 보안 기능을 제공하며, 많은 기능을 표준 Kubernetes API와 통합됩니다. Calico는 쿠버네티스의 Service, Pod, Deployment, Ingress 등과 같은 다양한 오브젝트를 지원하며, 플러그인 방식으로 설치되므로 다른 CNI 플러그인과도 호환됩니다. Calico는 네트워크 정책 및 보안 규칙 구현을 위한 강력한 도구를 제공하여 클러스터에서 매우 안전한 환경을 유지할 수 있습니다.</p>
<h3 id="구축한-클러스터">구축한 클러스터</h3>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/5e052bed-ac6b-42aa-9492-7a9548781307/image.png" alt=""></p>
<h1 id="트러블-슈팅">트러블 슈팅</h1>
<h2 id="1">1.</h2>
<p>Windows의 경우 다음과 같은 이더넷 속성을 설정해주어야 합니다</p>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/f664c154-49b1-4951-b6ce-8331a4d02507/image.png" alt=""></p>
<h2 id="2">2.</h2>
<p>pending 오류</p>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/4460a3f3-9947-48ba-992e-7abfd6c9dedc/image.png" alt=""></p>
<p>pod가 스케줄링 되지 않은 이유 검거하기</p>
<pre><code>kubectl describe pod httpd-deployment-57fc687dcc-krlws</code></pre><p>Events:
  Type     Reason            Age                 From               Message</p>
<hr>
<blockquote>
<p> Warning  FailedScheduling  26s (x21 over 22m)  default-scheduler  0/3 nodes are available: 1 node(s) had taint {node-role.kubernetes.io/master: }, that the pod didn&#39;t tolerate, 2 node(s) had taint {node.kubernetes.io/not-ready: }, that the pod didn&#39;t tolerate.</p>
<p>해석 : pod에 taints가 있어 해당 pod에 띄울 수 없다는 의미이다.
<img src="https://velog.velcdn.com/images/ssong_14/post/abe160f3-0688-4b2a-a900-0028994f5261/image.png" alt=""></p>
</blockquote>
]]></description>
        </item>
        <item>
            <title><![CDATA[Armv8 익셉션]]></title>
            <link>https://velog.io/@ssong_14/Armv8-%EC%9D%B5%EC%85%89%EC%85%98</link>
            <guid>https://velog.io/@ssong_14/Armv8-%EC%9D%B5%EC%85%89%EC%85%98</guid>
            <pubDate>Wed, 24 May 2023 17:38:25 GMT</pubDate>
            <description><![CDATA[<h1 id="익셉션-레벨">익셉션 레벨</h1>
<h2 id="익셉션-레벨은-무엇이고-왜-배워야-하는가">익셉션 레벨은 무엇이고 왜 배워야 하는가?</h2>
<h3 id="1-armv8-아키텍처를-이루는-기능을-이해하기-위해서">1. Armv8 아키텍처를 이루는 기능을 이해하기 위해서</h3>
<ul>
<li>익셉션 : 익셉션은 예외적인 상황이 발생했을 때 처리되는 이벤트 말합니다. 익셉션은 프로세서가 명령어를 실행하는 동안 발생할 수 있는 예기치 않은 상황을 나타냅니다. 익셉션이 유발되면 Arm core가 특정 엔트리 주소로 점프하게 됩니다.<ul>
<li>인터럽트  : 외부 디바이스나 하드웨어 이벤트로 인해 발생하는 익셉션 입니다</li>
<li>예외 : 명령어 실행중에 발생하는 오류나 예외상황으로 인한 익셉션</li>
<li>시스템 익셉션 : 아키텍처 전반에 걸쳐 발생하는 익셉션으로 프로세서의 동작에 영향을 주는 중요한 이벤트 처리를 합니다. 예를 들어 system call, 부동 소수점 연산 오류, 메모리 관리 오류 등이 습니다. </li>
</ul>
</li>
<li>하이퍼 바이저<ul>
<li>일반적으로 하이퍼바이저는 EL2 또는 EL1에서 동작하여 VM간의 격리와 리소스 할당을 하게 됩니다.</li>
</ul>
</li>
<li>트러스트존<ul>
<li>Arm 프로세서 아키텍처에서 제공하는 하드웨어 기반의 보안기술 입니다. TrustZone은 프로세서를 하나 이상의 보안 도메인으로 분리하여 각 도메인 간의 격리와 보안을 강화하는 것을 목표로 합니다.</li>
<li>트러스트존에 진입하기 위해서는 EL1에서 EL3으로 진입해야 합니다.</li>
</ul>
</li>
</ul>
<h3 id="2-익셉션-레벨의-정의">2. 익셉션 레벨의 정의</h3>
<p>Arm 아키텍처에서 프로세서의 권한 수준을 나타내는 데 사용되는 개념입니다. </p>
<ol>
<li>EL0 (Exception Level 0): 일반적인 응용 프로그램 및 운영체제의 사용자 모드로, 가장 낮은 권한 수준입니다. 주로 응용 프로그램이 실행되는 레벨입니다.</li>
<li>EL1 (Exception Level 1): 운영체제의 커널 모드로, EL0보다 높은 권한 수준을 가집니다. 운영체제의 커널이 실행되고 시스템 자원에 접근할 수 있습니다.</li>
<li>EL2 (Exception Level 2): 하이퍼바이저 모드로, 가상화 관련 작업을 수행합니다. 하이퍼바이저는 가상 머신(VM)을 관리하고 격리된 환경을 제공하는 역할을 합니다.</li>
<li>EL3 (Exception Level 3): 보안 모드로, 시스템의 가장 높은 권한 수준을 가집니다. 주로 보안 관련 작업과 초기화 및 부팅과정에서 사용됩니다.</li>
</ol>
<h2 id="익셉션">익셉션</h2>
<h3 id="synchronous-exception동기적-익셉션">Synchronous exception(동기적 익셉션)</h3>
<p>프로세서가 명령어를 실행하는 동안 발생하는 예외입니다. 이러한 익셉션은 현재 실행 중인 명령어와 밀접한 관련이 있으며, 해당 명령어의 실행 도중에 발생하는 예외 상황을 의미합니다.</p>
<h3 id="irq-익셉션">IRQ 익셉션</h3>
<p>프로세서에게 외부 장치나 이벤트로부터 인터럽트를 요청하는 신호입니다. IRQ 인터럽트는 프로세서의 실행을 중단하고, 특정 인터럽트 서비스 루틴(Interrupt Service Routine)을 실행하여 해당 인터럽트에 대한 처리를 수행합니다.</p>
<p>IRQ 인터럽트가 발생하면 프로세서는 현재 실행 중인 명령어를 중단하고, 예외 처리 메커니즘을 통해 IRQ 예외 루틴으로 제어를 전환합니다. 이때 인터럽트 처리를 위한 전처리 작업이 수행되고, 해당 IRQ 예외 루틴이 실행됩니다. IRQ 예외 루틴은 프로세서가 인터럽트 서비스를 처리하는 코드로 이동하여, 외부 장치의 요청에 따른 작업을 수행합니다.</p>
<h3 id="esr-exception-syndrome-register">ESR (Exception Syndrome Register)</h3>
<p>Arm 아키텍처에서 예외 발생 시 예외의 세부 정보를 저장하는 레지스터입니다.</p>
<p>ESR은 예외 유형, 예외 원인, 예외 상태 등과 같은 다양한 정보를 제공하여 예외처리에 도움을 줍니다.</p>
<p>EC를 포함하고 있습니다.</p>
<h2 id="기타-용어들">기타 용어들</h2>
<h3 id="ec-exception-class">EC (Exception Class)</h3>
<p>익셉션이 유발된 세부 유발 인자입니다.</p>
<h3 id="pstate">pstate</h3>
<p>Armv8 아키텍처에서 사용되는 제어 및 상태 정보를 포함하는 레지스터입니다. PSTATE 레지스터는 현재 프로세서의 실행 상태와 프로그램 제어에 관련된 여러 플래그를 저장합니다.</p>
<p><br><br><br></p>
<h2 id="armv8-아키텍처에서-익셉션을-처리하는-방식">Armv8 아키텍처에서 익셉션을 처리하는 방식</h2>
<ul>
<li>익셉션이 발생했다고 감지하면 익셉션 종류별로 이미 정해놓은 주소로 프로그램 카운터를 브랜치합니다 </li>
<li>이미 정해진 주소를 익셉션 벡터 주소라 하며, 각 익셉션의 종류에 따라 익셉션 벡터 주소의 위치가 다릅니다 (실제로는 익셉션 벡터 테이블에 명시된 주소로 점프하는 것이 아닌 벡터 테이블의 엔트리 주소(base addr)에 테이블에 해당하는 주소값을 더한 주소로 이동합니다.)</li>
<li>익셉션 벡터 주소에는 익셉션을 핸들링하는 코드가 있습니다.</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[네트워크 패킷 흐름과 ARP 프로토콜]]></title>
            <link>https://velog.io/@ssong_14/%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC-%ED%8C%A8%ED%82%B7-%ED%9D%90%EB%A6%84%EA%B3%BC-ARP-%ED%94%84%EB%A1%9C%ED%86%A0</link>
            <guid>https://velog.io/@ssong_14/%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC-%ED%8C%A8%ED%82%B7-%ED%9D%90%EB%A6%84%EA%B3%BC-ARP-%ED%94%84%EB%A1%9C%ED%86%A0</guid>
            <pubDate>Wed, 24 May 2023 10:19:41 GMT</pubDate>
            <description><![CDATA[<h2 id="리눅스-네트워크-기반-패킷-흐름">리눅스 네트워크 기반 패킷 흐름</h2>
<p><img src="https://velog.velcdn.com/images/ssong_14/post/4207f0f3-cc44-4c07-abc9-16d8a164f05a/image.png" alt=""></p>
<ol>
<li>이더넷이 전기적인 신호를 받아들입니다.</li>
<li>네트워크 인터페이스 카드(NIC)에 해당하는 네트워크 디바이스 드라이버가 비트를 바탕으로 프레임을 만듭니다. (Frame : 48bit)</li>
<li>이더넷 프레임 핸들러는 이 프레임의 헤더를 보고 MAC 주소(하드웨어 주소)를 확인하여 장치나 호스트를 식별합니다.</li>
<li>식별한 호스트가 맞을 경우 IP 로 보내고 해당 IP가 어떤 방식인지 확인하여 TCP 또는 UDP 로 전송하게 됩니다.</li>
<li>응용프로그램에서 소켓 인터페이스를 통해 각각의 데이터를 송/수신하게 됩니다.</li>
</ol>
<p>2~4번의 과정이 OS에서 관리하는 부분입니다.</p>
<p>인터넷으로 기반으로 통신하기 위해서는 반드시 3가지 정보를 알아야 합니다</p>
<p><strong>MAC Address</strong>,<strong>IP Address</strong>, <strong>Port</strong></p>
<ul>
<li>MAC Address : 48비트 하드웨어 주소. 물리적인 네트워크 장치에 부여되며, L2에서 사용됩니다.
MAC 주소는 공장에서 NIC에 할당되며 전 세계적으로 고유합니다. (<code>00:1A:2B:3C:4D:5E</code>)</li>
<li>IP Address : L3에서 사용되며 데이터 패킷이 전송되는 경로를 결정하는데 사용합니다. IPv4는 32비트로 구성된 주소체계입니다. 주로 네트워크에서 사용되며 &quot;x.x.x.x&quot;로 표현됩니다.</li>
<li>Port : 16비트로 구성되며 0~ 65535까지의 값으로 서비스나 응용프로그램이 특정한 네트워크 주소에서 통신할 수 있도록 식별합니다.</li>
</ul>
<h5 id="그렇다면-우리가-구글에-접속할-때-mac-address구글-서버-하드웨어-주소는-모르는데-어떻게-접속할까요">그렇다면 우리가 구글에 접속할 때 MAC Address(구글 서버 하드웨어 주소)는 모르는데 어떻게 접속할까요?</h5>
<h4 id="arp-프로토콜">ARP 프로토콜</h4>
<p>네트워크에서 IP 주소를 해당하는 MAC 주소로 매핑하기 위해 사용되는 프로토콜입니다.</p>
<p>ARP는 다음과 같은 주요 단계로 작동합니다:</p>
<ol>
<li>호스트 A는 목적지 IP 주소에 대한 데이터를 전송하려고 할 때, 자신의 ARP 캐시 (ARP Cache)를 확인합니다. ARP 캐시는 이전에 요청한 IP 주소에 대한 MAC 주소 매핑을 저장하고 있습니다.</li>
<li>만약 ARP 캐시에 목적지 IP 주소에 대한 MAC 주소 매핑이 없다면, 호스트 A는 네트워크 상에서 ARP 요청 패킷을 브로드캐스트합니다. 이 ARP 요청 패킷에는 목적지 IP 주소가 포함되어 있습니다.</li>
<li>네트워크 상의 모든 호스트는 ARP 요청 패킷을 수신하고, 자신의 IP 주소와 비교하여 일치하는 경우에만 ARP 응답 패킷을 보냅니다. ARP 응답 패킷에는 MAC 주소가 포함되어 있습니다.</li>
<li>호스트 A는 ARP 응답 패킷을 수신하고, 이를 통해 목적지 IP 주소에 대한 MAC 주소를 알게 됩니다. 이후 호스트 A는 목적지 MAC 주소를 사용하여 데이터를 전송합니다.</li>
</ol>
<p>ARP는 동일한 로컬 네트워크 상에서 동작하며, 네트워크 계층의 IP 주소와 데이터 링크 계층의 MAC 주소 간의 상호 변환을 수행합니다. ARP를 사용함으로써 호스트는 목적지 MAC 주소를 알고 효율적인 네트워크 통신을 할 수 있습니다.</p>
]]></description>
        </item>
        <item>
            <title><![CDATA[OSI 7 Layer (네트워크 인프라를 중심으로)]]></title>
            <link>https://velog.io/@ssong_14/OSI-7-Layer-%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC-%EC%9D%B8%ED%94%84%EB%9D%BC%EB%A5%BC-%EC%A4%91%EC%8B%AC%EC%9C%BC%EB%A1%9C</link>
            <guid>https://velog.io/@ssong_14/OSI-7-Layer-%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC-%EC%9D%B8%ED%94%84%EB%9D%BC%EB%A5%BC-%EC%A4%91%EC%8B%AC%EC%9C%BC%EB%A1%9C</guid>
            <pubDate>Wed, 24 May 2023 09:34:39 GMT</pubDate>
            <description><![CDATA[<h2 id="osi-7-layer">OSI 7 Layer</h2>
<p>컴퓨터 네트워크 프로토콜 디자인과 통신을 계층으로 나누어 설명한 것입니다.</p>
<h3 id="l1---physical-layer">L1 - Physical Layer</h3>
<p>이더넷 케이블, 네트워크 카드 같은 하드웨어 장치들을 의미합니다</p>
<p>이 계층에서의 통신은 비트의 흐름으로 되어 있습니다.</p>
<p>전압의 크기차이로 (GROUND를 기준으로 전압의 크기를 나눔 기준보다 높으면 1 낮으면 0 )</p>
<p>비트를 구분합니다.</p>
<p>이 비트를 이해하기 위한 장치를 네트워크 카드라고 합니다.</p>
<p>네트워크 카드는 케이블(이더넷 케이블)에서 주고받는 데이터를 처리하는 데 이 데이터의 기본 단위를 <strong>프레임</strong>이라고 합니다.</p>
<blockquote>
<p>네트워크 프레임</p>
<p>데이터 통신에서 전송되는 기 단위로, 네트워크에서 데이터를 패킷 단위로 분할하여 전송하는 과정에서 사용됩니다. 프레임은 일련의 비트로 구성되며, 헤더, 페이로드(데이터)(, 트레일러)로 구성됩니다.</p>
<p>송신자는 데이터를 프레임으로 분할하여 네트워크를 통해 전송하고, 수신자는 프레임을 재조립하여 원래 데이터로 복구합니다.</p>
</blockquote>
<p><br><br></p>
<h3 id="l2---data-link-layer">L2 - Data Link Layer</h3>
<p>하드웨어의 특징들에 따라 달라지는 구조를 가지는 계층을 말합니다.</p>
<p>이 계층은 물리적인 연결 위에 구축되며, 데이터를 프레임이라는 작은 블록으로 분할하고 전송합니다.</p>
<ul>
<li><p>프레임 동기화 : 송신자와 수신자 사이에서 프레임의 시작과 끝을 동기화하여 송신자가 전송하는 데이터를 수신자가 올바르게 인식하고 해석할 수 있도록 보장하는 중요한 단계입니다.</p>
<ul>
<li>동기화 방법으로는 bit string synchronization(시작을 알리기 위한 고유한 비트 시퀀스 전송)와 자리 동기화(특정한 비트 위치를 기준으로 프레임의 시작을 식별하는 방법) 이 있습니다.</li>
</ul>
</li>
<li><p>오류 감지 : 프레임 전송 중 발생한 오류를 검출합니다. (CRC)</p>
</li>
<li><p>흐름 제어 : 송/수신자간의 데이터 흐름을 조절하여 네트워크 혼잡을 방지하고 데이터의 손실을 최소화합니다.</p>
<ul>
<li>Stop-and-Wait : 데이터 전송 후 수신 확인 신호(ACK)를 기다림으로써 송신자는 다음 데이터를 전송하기 전에 수신 확인을 받아야 합니다. </li>
<li>슬라이딩 윈도우 : 수신자는 송신자로부터 받을 수 있는 데이터의 양을 미리 알려주고, 송신자는 해당 윈도우 내에서만 데이터를 전송할 수 있습니다.</li>
</ul>
</li>
<li><p>링크 관리 : 물리적인 연결이 설정되고 링크에 필요한 자원을 할당합니다.</p>
</li>
</ul>
<p><br><br></p>
<h3 id="l3---network-layer">L3 - Network Layer</h3>
<p>비교적 하드웨어에 독립적인 layer 입니다.</p>
<p>네트워크 간의 데이터 전송을 관리하고 경로 선택과 패킷 전달 등의 역할을 수행합니다.</p>
<ul>
<li>패킷 전달 : 송신자로부터 수신자까지 전달하는 역할을 합니다. 경로 선택은 라우팅 알고리즘에 의해 이루어집니다.</li>
<li>라우팅 : 송신자가 수신자에게 패킷을 전달하기 위해 사용되는 경로 선택 프로세스입니다. 라우팅 테이블을 사용하여 네트워크 상의 다양한 목적지에 대한 경로 정보를 저장하고 이를 기반으로 패킷을 전달합니다</li>
<li>흐름 제어 </li>
<li>패킷 분할 및 조립</li>
<li>주소할당 : 각 호스트 및 라우터에 고유한 주소를 할당하는 역할을 합니다. IP주소는 L3계층에서 사용됩니다.</li>
</ul>
<p><br><br></p>
<h3 id="l4---transport-layer">L4 - Transport Layer</h3>
<p>데이터를 보내는 방식을 결정하는 layer입니다. 우리가 일반적으로 많이 접하게되는 TCP/UDP에 대한 방식이 여기에서 결정됩니다.</p>
<p>L4가 담당하는 기능들은 다음과 같습니다.</p>
<ul>
<li>연결 설정과 해제</li>
<li>데이터 분할 및 조립</li>
<li>흐름 제어</li>
<li>오류 검출 및 복구</li>
<li>다중화 및 역다중화</li>
</ul>
<p>이와 관련한 내용은 <a href="https://velog.io/@ssong_14/%EC%9D%B8%ED%84%B0%EB%84%B7-%EB%84%A4%ED%8A%B8%EC%9B%8C%ED%81%AC">여기</a>에서 확인 바랍니다.</p>
<p><br><br></p>
<h3 id="l5---session-layer">L5 - Session Layer</h3>
<ul>
<li><p>세션 관리: L5는 응용 프로그램 간의 세션을 설정, 유지 및 종료하는 기능을 제공합니다. 세션은 통신이 시작되고 종료되는 동안의 상호 작용을 나타내며, 동기화, 대화 제어, 체크포인트 등의 기능을 포함합니다.
<br><br></p>
<h3 id="l6---presentation-layer">L6 - Presentation Layer</h3>
</li>
<li><p>데이터 형식 변환: L6는 데이터의 형식 변환과 암호화, 압축 등의 데이터 변환 기능을 제공합니다. 이 계층은 응용 프로그램이 서로 다른 데이터 형식을 사용하더라도 상호 운영이 가능하도록 데이터를 변환하고, 데이터의 표현 방식에 대한 협상을 수행합니다.
<br><br></p>
<h3 id="l7---application-layer">L7 - Application Layer</h3>
</li>
<li><p>응용 프로그램 서비스: L7은 최종 사용자에게 제공되는 응용 프로그램 서비스를 담당합니다. 이 계층은 네트워크 상에서 동작하는 다양한 응용 프로그램들을 지원하며, 이메일, 웹 브라우저, 파일 전송, 동영상 스트리밍 등과 같은 서비스를 제공합니다.</p>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[리눅스 셸]]></title>
            <link>https://velog.io/@ssong_14/%EB%A6%AC%EB%88%85%EC%8A%A4-%EC%85%B8</link>
            <guid>https://velog.io/@ssong_14/%EB%A6%AC%EB%88%85%EC%8A%A4-%EC%85%B8</guid>
            <pubDate>Fri, 12 May 2023 19:47:58 GMT</pubDate>
            <description><![CDATA[<h1 id="셸의-기능">셸의 기능</h1>
<h3 id="명령어-해석기-기능-프로그래밍-기능-사용자-환경-설정-기능">명령어 해석기 기능, 프로그래밍 기능, 사용자 환경 설정 기능</h3>
<ul>
<li>명령어 해석기 기능<ul>
<li>사용자와 커널 사이에서 명령을 해석하여 전달하는 해석기와 번역기 기능입니다.</li>
<li>사용자가 로그인하면 셸이 자동으로 실행되어 사용자가 명령을 입력하기를 기다립니다.</li>
<li>로그인 셸은 /etc.passwd 파일에 사용자별로 지정할 수 있습니다.</li>
<li>프롬프트 : 셸이 사용자의 명령을 기다리고 있음을 나타내는 표시합니다.</li>
</ul>
</li>
<li>프로그래밍 기능<ul>
<li>셸은 자체 내에 프로그래밍 기능이 있어 반복적으로 수행하는 작업을 하나의 프로그램으로 작성 할 수 있습니다.</li>
<li>셸 프로그램을 셸 스크립트라고 합니다.</li>
</ul>
</li>
<li>사용자 환경 설정 기능<ul>
<li>사용자 환경을 설정할 수 있도록 초기화 파일 기능 제공</li>
<li>초기화 파일에는 명령을 찾아오는 경로를 설정하거나, 파일과 디렉터리를 새로 생성할 때 기본 권한을 설정하거나, 다양한 환경 변수 등을 설정</li>
</ul>
</li>
</ul>
<h3 id="기본-셸-바꾸기">기본 셸 바꾸기</h3>
<p>chsh : /bin/bash 의 bash 셸을 변경하는 명령어. 사용자 로그인 셸을 바꿉니다.</p>
<ul>
<li>-s shell : 지정한 셸로 로그인 셸을 바꿉니다.</li>
<li>-l : /etc/shells 파일에 지정된 셸을 출력합니다.</li>
</ul>
<h3 id="로그인-셸과-서브-셸">로그인 셸과 서브 셸</h3>
<ul>
<li>프롬프트에서 다른 셸을 실행할 수 있는데 이를 서브 셸이라 합니다.</li>
<li>서브 셸은 또 다른 서브 셸 생성 가능합니다.</li>
</ul>
<h3 id="셸-내장-명령">셸 내장 명령</h3>
<ul>
<li>셸을 자체적으로 내장 명령을 가지고 있습니다.</li>
<li>셸 내장 명령은 별도의 실행 파일이 없고 셸 안에 포함되어 있습니다.<ul>
<li>예 : cd</li>
</ul>
</li>
</ul>
<h3 id="배시-셸의-출력-명령">배시 셸의 출력 명령</h3>
<ul>
<li><p>echo : 화면에 한 줄의 문자열을 출력합니다.</p>
<ul>
<li>echo [-n] 문자열 </li>
<li>-n : 마지막에 줄 바꿈을 하지 않습니다.</li>
</ul>
</li>
<li><p>printf : %지시자와 \ 문자를 이용하여 출력 형식을 지정 가능합니다.</p>
<ul>
<li>자료를 형식화 하여 화면에 출력합니다.</li>
<li>인수 전달이 가능하고 c언어 printf 함수의 형식을 지정합니다.</li>
</ul>
</li>
</ul>
<h3 id="특수문자-사용하기">특수문자 사용하기</h3>
<p>명령을 입력하면 셸은 먼저 특수문자가 있는지 확인하고 이를 적절한 형태로 변경한 후 명령을 실행합니다.</p>
<ul>
<li><p>*: 임의의 문자열을 나타내는 특수문자로 0개 이상의 문자로 대체합니다</p>
</li>
<li><p>?와 [] : ? 는 글자 하나 []는 정규식과 유사합니다.</p>
</li>
<li><p>~/- : 디렉터리를 나타내는 특수문자</p>
</li>
<li><p>~만 사용하면 현재 작업중인 사용자의 홈 디렉토리입니다.</p>
</li>
<li><p>-는 cd 명령으로 디렉터리를 이전하기 직전의 작업 디렉토리 표시</p>
</li>
<li><p>; : 명령과 명령을 연결합니다.</p>
</li>
<li><p>|(파이프) : 왼쪽 명령의 실행 결과를 오른쪽 명령의 입력으로 전달 ( <a href="https://velog.io/@ssong_14/%EC%8B%9C%EC%8A%A4%ED%85%9C-%EC%BD%9C-fork-exec-pipe">시스템 콜</a> )</p>
</li>
<li><p>&#39;&#39; , &quot; &quot; :  작은 따옴표는 모든 특수 문자를 큰따옴표는 $,``,\ 를 제외한 모든 특수문자를 일반 문자로 간주</p>
</li>
<li><p>` : 명령으로 해석하여 명령의 실행 결과로 전달</p>
</li>
<li><p>\ : 특수문자를 일반문자로 처리</p>
</li>
<li><p>&lt;,&gt;,&gt;&gt; : 입출력의 방향을 바꾸는 특수 문자입니다.
<strong>입출력 방향 바꾸기</strong>
출력 리다이렉션</p>
<ul>
<li><p>&gt; : 기존 파일의 내용을 삭제하고 새로 결과를 저장합니다. ( 파일 덮어 쓰기 )</p>
<ul>
<li><p>명령1 &gt; 파일
<img src="https://velog.velcdn.com/images/ssong_14/post/6528754a-0078-4d59-b5fa-cb477dfcd944/image.png" alt=""></p>
</li>
<li><p>다음 옵션으로 예상치 않게 파일의 내용이 겹쳐 쓰이는 상황 예방할 수 있습니다.</p>
</li>
</ul>
</li>
<li><p>set -o noclobber (설정)</p>
</li>
<li><p>set +o noclobber (해제)</p>
</li>
<li><p>&gt;&gt; : 기존 파일의 내용 뒤에 결과를 추가합니다. (ex:log)</p>
</li>
</ul>
</li>
</ul>
]]></description>
        </item>
        <item>
            <title><![CDATA[Linux File and Directory]]></title>
            <link>https://velog.io/@ssong_14/Linux-File-and-Directory</link>
            <guid>https://velog.io/@ssong_14/Linux-File-and-Directory</guid>
            <pubDate>Fri, 12 May 2023 19:39:29 GMT</pubDate>
            <description><![CDATA[<h1 id="리눅스-파일의-종류와-특징">리눅스 파일의 종류와 특징</h1>
<p>파일 : 관련있는 정보들의 집합</p>
<h2 id="종류">종류</h2>
<ul>
<li>일반 파일 : 데이터를 저장하는데 주로 사용하며 각종 테스트 파일, 실행 파일, 이미지 파일 등 리눅스에서 사용하는 대부분의 파일들은 일반 파일에 해당합니다.</li>
<li>디렉터리 : 리눅스는 디렉터리도 파일로 취급합니다. 디렉터리 파일에는 해당 디렉터리에 저장된 파일이나 하위 디렉터리에 대한 정보가 저장되어 있습니다.</li>
<li>심벌릭 링크 (Windows의 바로가기) : 원본 파일을 대신하여 다른 이름으로 파일명을 지정한 것</li>
<li>장치 파일(/dev 하위 파일) : 리눅스에서는 하드디스크나 키보드 같은 장치도 파일로 취급합니다. </li>
</ul>
<h2 id="디렉터리의-계층-구조">디렉터리의 계층 구조</h2>
<ul>
<li><p>리눅스에서는 파일을 효율적으로 관리하기 위해 디렉터리를 계층적으로 구성합니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/dcd041ec-e32f-4c89-8430-29ff953c8c9c/image.png" alt=""></p>
<blockquote>
<p>tree 패키지를 이용한 디렉터리 구조</p>
</blockquote>
</li>
<li><p>모든 디렉터리의 출발점은 루트(root) 디렉터리이며, / 으로 표시합니다
<img src="https://velog.velcdn.com/images/ssong_14/post/d445561d-a357-441d-98b8-28f508985e60/image.png" alt=""></p>
<blockquote>
<p>-F 옵션 : 디렉터리일 경우 /를 심벌릭 링크일 경우 @를 붙여서 표시
파일 이름 앞에 . 이 붙는 경우 숨김파일입니다.</p>
</blockquote>
</li>
</ul>
<h2 id="자주-쓰는-파일디렉터리-명령어">자주 쓰는 파일/디렉터리 명령어</h2>
<ul>
<li><p>pwd : print working directory, 현재 위치한 디렉토리를 출력합니다.</p>
</li>
<li><p>cd : 지정한 디렉터리로 이동</p>
</li>
<li><p>ls : 디렉터리의 내용을 출력합니다. </p>
</li>
<li><p>cat : 텍스트 파일 내용을 확인합니다.</p>
</li>
<li><p>mkdir/rmdir : 디렉터리를 생성/삭제 합니다.</p>
</li>
<li><p>more : 파일 내용을 화면 단위로 출력합니다.</p>
</li>
<li><p>tail : 파일 뒷부분의 몇 행을 출력합니다. (주로 로그 확인할 때 사용)</p>
</li>
<li><p>cp : 파일이나 디렉터리를 복사합니다.</p>
</li>
<li><p>mv : 파일을 이동합니다.</p>
</li>
<li><p>rm : 파일을 삭제합니다.</p>
</li>
<li><p>touch : 빈 파일을 생성합니다.</p>
</li>
<li><p>grep : 지정한 패턴이 포함된 행을 찾습니다.</p>
</li>
<li><p>find : 지정한 위치에서 조건에 맞는 파일을 찾습니다. 
  <code>-name 파일명 -type 파일종류 -user 로그인아이디</code></p>
</li>
<li><p>whereis, which : 파일의 위치를 찾습니다.
<img src="https://velog.velcdn.com/images/ssong_14/post/71fac90c-04ff-47c9-b015-c7cb7233c7a2/image.png" alt=""></p>
</li>
</ul>
<h2 id="파일">파일</h2>
<p>리눅스 파일의 구성</p>
<ul>
<li>파일 = 파일명 + inode + 데이터블록<ul>
<li>inode : 파일에 대한 정보를 가지고 있는 특별한 구조체 입니다. 외부적으로는 번호로 표시되고 내부적으로는 파일의 종류 및 크기, 소유자, 파일 변경 시간 등 상세 정보와 데이터 블록의 주소를 저장합니다. </li>
</ul>
</li>
</ul>
]]></description>
        </item>
    </channel>
</rss>