<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
  <channel>
    <title>Hosang's Homepage</title>
    <link>https://hahaite.tistory.com/</link>
    <description></description>
    <language>ko</language>
    <pubDate>Sat, 4 Jul 2026 09:00:20 +0900</pubDate>
    <generator>TISTORY</generator>
    <ttl>100</ttl>
    <managingEditor>상사꽃</managingEditor>
    <item>
      <title>Unary Function 사용예제. for_each() 함수</title>
      <link>https://hahaite.tistory.com/330</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;Unary Function 은 인자가 1개이며 아무 반환값을 갖는 함수를 말한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;int test1(int a) ;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;char test2(string strText) ;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;void test3(char* p) ;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위 세 함수 모두 Unary Function 타입이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;한마디로, 한개의 인자를 가진 함수이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;c++ std::for_each 함수의 원형은 아래와 같다.&lt;/p&gt;
&lt;pre id=&quot;code_1746700873301&quot; style=&quot;background-color: #f8f8f8; color: #383a42; text-align: start;&quot; data-ke-type=&quot;codeblock&quot; data-ke-language=&quot;cpp&quot;&gt;&lt;code&gt;namespace std {
    template&amp;lt;class InputIt, class UnaryFunction&amp;gt;
    UnaryFunction for_each(InputIt first, InputIt last, UnaryFunction f);
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;복잡한 거 빼고,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위에 적혀있는 Unary Function 에, 한개의 인자를 가진 함수를 변수로 가진다 할 수 있겠다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래는 예제이다.&lt;/p&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&amp;clubs; for_each() + 함수포인터&lt;/span&gt;&lt;/b&gt;&lt;/h4&gt;
&lt;pre id=&quot;code_1746701203848&quot; class=&quot;cpp&quot; data-ke-language=&quot;cpp&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;#include &amp;lt;cstdio&amp;gt;
#include &amp;lt;algorithm&amp;gt;

using namespace std ;

int printList(int a)
{
        printf(&quot;a : %d\n&quot;, a) ;
        return 1 ;
}

int main()
{
        int data[5] = {3, 5, 1, 13, 7} ;

        // Unary Function - printList
        // by 함수포인터를 사용한 방법
        for_each(&amp;amp;data[0], &amp;amp;data[4], &amp;amp;printList) ;

        return 1 ;
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;printList 함수는 한개의 인자를 가진 함수이므로 Unary Function 이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 함수를 for_each() 함수의 세번째에 함수포인터로 전달하고 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그러면 for_each() 함수는 data 배열의 값을 하나씩 printList 함수의 인자로 전달하고,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그 값이 전달될 때마다 printList() 함수는 호출된다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;324&quot; data-origin-height=&quot;122&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bIPOWa/btsNPg8SLtU/s3j8r5NEnKzj7maOJ88Nx0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bIPOWa/btsNPg8SLtU/s3j8r5NEnKzj7maOJ88Nx0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bIPOWa/btsNPg8SLtU/s3j8r5NEnKzj7maOJ88Nx0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbIPOWa%2FbtsNPg8SLtU%2Fs3j8r5NEnKzj7maOJ88Nx0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;324&quot; height=&quot;122&quot; data-origin-width=&quot;324&quot; data-origin-height=&quot;122&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h4 data-ke-size=&quot;size20&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; for_each() + 함수객체 (Functor)&lt;/b&gt;&lt;/span&gt;&lt;/h4&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;함수객체는 굵고 짧게 얘기하면, 클래스 객체를 함수처럼 사용하겠다는 말이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;예를 들어 아래처럼 test 란 클래스 객체를 생성했다 치자.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #0000ff;&quot;&gt;MyTest test = MyTest() ;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 때, test 객체는 보통 아래처럼 쓰인다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #0000ff;&quot;&gt;test.init() ;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #0000ff;&quot;&gt;test.destroy() ;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그런데 함수 객체(Functor) 처럼 구현되면 아래처럼 호출할 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #0000ff;&quot;&gt;test(5) ;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;test 는 분명 MyTest 클래스의 객체인데 마치 함수처럼 사용되고 있는 것이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;대단하게 썼지만 연산자 오버로딩으로 구현했을 뿐이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;본론으로 돌아와서,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Unary Function 에는 위 함수객체 또한 포함된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래는 그 예제이다.&lt;/p&gt;
&lt;pre id=&quot;code_1746704220277&quot; class=&quot;cpp&quot; data-ke-language=&quot;cpp&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;#include &amp;lt;cstdio&amp;gt;
#include &amp;lt;algorithm&amp;gt;

using namespace std ;

class TotalSum
{
public :
        int getSum(){ return sum; } ;

        // 아래 구현된 연산자 오버로딩으로 객체를 함수처럼 사용할 수 있다.
        void operator() (int x)
        {
                sum += x ;
        }

private :
        int sum ;

};

int main()
{
        int data[5] = {3, 5, 1, 13, 7} ;

        // 함수 객체 (Functor) 를 이용한 방법

        // for_each 함수의 반환값은 Unary Function 이다.
        // 함수포인터의 경우, 이 반환값은 무시된다.
        // 하지만 함수객체는 아래처럼 반환값을 받을 수 있다.
        TotalSum temp = TotalSum() ;
        TotalSum sum1 = for_each(&amp;amp;data[0], &amp;amp;data[5], temp) ;
        printf(&quot;Sum1 : %d\n&quot;, sum1.getSum()) ;

        // 굳이 클래스객체를 생성해서 넘기지 않아도 된다.
        TotalSum sum2 = for_each(&amp;amp;data[0], &amp;amp;data[5], TotalSum()) ;
        printf(&quot;Sum2 : %d\n&quot;, sum2.getSum()) ;

        return 1 ;
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;h4 style=&quot;color: #000000; text-align: start;&quot; data-ke-size=&quot;size20&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; for_each() + 람다함수 ( Lamda Function)&lt;/b&gt;&lt;/span&gt;&lt;/h4&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;함수포인터, 함수객체의 경우, main 함수 밖에서 따로 구현된 코드가 존재한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;람다함수를 사용하면 for_each() 세번째 인자에서 바로 함수를 구현하여&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;코드를 직관적으로 짤 수 있고 inline 처럼 구현되어 프로그램 실행속도도 빨라진다고 함.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;람다함수는 나도 아리까리해서 그냥 예제로 퉁친다.&lt;/p&gt;
&lt;pre id=&quot;code_1746704653158&quot; class=&quot;cpp&quot; data-ke-language=&quot;cpp&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;#include &amp;lt;cstdio&amp;gt;
#include &amp;lt;algorithm&amp;gt;

using namespace std ;

int main()
{
        int data[5] = {3, 5, 1, 13, 7} ;

        // Lamda 함수를 이용한 방법
        // Lamda 함수는 함수객체처럼 누적된 변수를 가질 수 없다.
        // C++14 이상의 mutable 을 사용하거나 외부 변수를 사용한다.사용한다
        // 아니면 위와 같이 합을 구하는 경우, accumulate() 함수를 사용할 수 있다.

        // 아래는 Lamda 함수를 사용해 값을 출력하는 방법이다.

        // 한줄 출력
        for_each( &amp;amp;data[0], &amp;amp;data[5], [](int a) { printf(&quot;a1 : %d\n&quot;, a);});
        printf(&quot;===================\n&quot;) ;

        // 인자 분해.
        for_each(
                &amp;amp;data[0],
                &amp;amp;data[5],
                [](int a)
                {
                        printf(&quot;a2 : %d\n&quot;, a);
                }
        );

        return 1 ;
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;몇년 전, 당췌 봐도 뭔소리인지 모르던 개념 (Unary Function, functor, 람다함수 등) 이&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이제야 살짝 이해가 가서 정리해 본다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/C,C++</category>
      <category>for_each</category>
      <category>Functor</category>
      <category>unary function</category>
      <category>unaryfunction</category>
      <category>람다함수</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/330</guid>
      <comments>https://hahaite.tistory.com/330#entry330comment</comments>
      <pubDate>Thu, 8 May 2025 20:48:41 +0900</pubDate>
    </item>
    <item>
      <title>특정시간에 실행하는 타이머 설정하기</title>
      <link>https://hahaite.tistory.com/329</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;clubs; 도움받은 사이트&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://wiki.archlinux.org/title/Systemd/Timers&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://wiki.archlinux.org/title/Systemd/Timers&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;특정 시간에 뭔가를 실행하기 위해 타이머를 설정하는 방법을 다룬다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;나같은 경우, 서버의 DB 를 백업하는 용도로 사용하였다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;cron 이나 systemd 를 사용하는 방법이 있는데 요새 추세가 systemd 를 사용하는 듯 하다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;/etc/systemd/system 밑에 두개의 파일을 생성하고 아래처럼 작성한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(&lt;span style=&quot;color: #ee2323;&quot;&gt;파일명 및 내용은 본인 환경에 맞게 적절히 수정하여 사용한다.&lt;/span&gt;)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;clubs; 1. mdb_backup.service&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;$ &lt;span style=&quot;color: #006dd7;&quot;&gt;cd /etc/systemd/system&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;$ &lt;span style=&quot;color: #006dd7;&quot;&gt;sudo vi mdb_backup.service&lt;/span&gt;&lt;/p&gt;
&lt;pre id=&quot;code_1735817598084&quot; class=&quot;css&quot; data-ke-language=&quot;css&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;[Unit]
Description=Run MariaDB Backup

[Service]
Type=oneshot
ExecStart=/bin/bash /home/hahaite/MDB_Backup/backup.sh&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;타이머가 발동(?) 되면 /home/hahaite/MDB_Backup 밑에 backup.sh 스크립트를 실행한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;실행할 프로그램 등을 위 스크립트에 작성하여 실행한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;clubs; 2. mdb_backup.timer&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;$ &lt;span style=&quot;color: #006dd7;&quot;&gt;cd /etc/systemd/system&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;$ &lt;span style=&quot;color: #006dd7;&quot;&gt;sudo vi mdb_backup.timer&lt;/span&gt;&lt;/p&gt;
&lt;pre id=&quot;code_1735817953573&quot; class=&quot;css&quot; data-ke-language=&quot;css&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;[Unit]
Description=MariaDB Backup

[Timer]
OnCalendar=*-*-* 11:00
OnCalendar=*-*-* 13:00
OnCalendar=*-*-* 15:30
OnCalendar=*-*-* 18:00
OnCalendar=*-*-* 20:10
Unit=mdb_backup.service

[Install]
WantedBy=timers.target&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;매일 5번, mdb_backup.service (위에 작성한 것) 를 실행한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(구글링하면 수많은 예제가 있는데 위 코드가 직관적이여서 선호하는 방식이다.)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;clubs; 서비스 등록&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Linux 시작 시, 자동 시작되도록 서비스를 등록한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;$ &lt;span style=&quot;color: #006dd7;&quot;&gt;sudo systemctl enable mdb_backup.timer&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;clubs; 바로 타이머 시작&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;지금 바로 타이머를 시작한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;$ &lt;span style=&quot;color: #006dd7;&quot;&gt;sudo systemctl start mdb_backup.timer&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;clubs; 현재 등록된 타이머 확인&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;타이머가 정상적으로 등록 및 시작되면 아래 명령어로 확인할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;$ &lt;span style=&quot;color: #006dd7;&quot;&gt;sudo systemctl list-timers&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;b&gt;&amp;clubs; 타이머 재등록 (re-load)&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위 두 파일을 수정한 경우, 아래 명령어로 리로드(Reload) 한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;$ &lt;span style=&quot;color: #006dd7;&quot;&gt;sudo systemctl daemon-reload&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/Linux</category>
      <category>linux timer</category>
      <category>ubuntu timer</category>
      <category>리눅스 타이머</category>
      <category>우분투 타이머</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/329</guid>
      <comments>https://hahaite.tistory.com/329#entry329comment</comments>
      <pubDate>Thu, 2 Jan 2025 20:49:43 +0900</pubDate>
    </item>
    <item>
      <title>정규 표현식 모음</title>
      <link>https://hahaite.tistory.com/328</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;코드에서 사용한 정규표현식을 이래저래 모아본다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;clubs; 특정문자 없애기&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;문장 :&amp;nbsp; &amp;nbsp; &amp;nbsp; -25&amp;nbsp; &amp;nbsp;dBm&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;기대 : dBm 을 없앤다.&lt;/p&gt;
&lt;pre id=&quot;code_1726723597537&quot; class=&quot;cpp&quot; style=&quot;background-color: #f8f8f8; color: #383a42;&quot; data-ke-type=&quot;codeblock&quot; data-ke-language=&quot;cpp&quot;&gt;&lt;code&gt;        strValue = regex_replace(&quot;   -25  dBm&quot;, regex(&quot;dBm&quot;), &quot;&quot;) ;
        printf(&quot;result : [%s]\n&quot;, strValue.c_str()) ;&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;결과 : [&amp;nbsp; &amp;nbsp; -25&amp;nbsp; &amp;nbsp;]&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;clubs; 양쪽 공백 없애기 ( 스페이스, 탭, 줄바꿈 등 )&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;문장 :&amp;nbsp; &amp;nbsp;\t&amp;nbsp; &amp;nbsp;-25&amp;nbsp; &amp;nbsp;dBm&amp;nbsp; \n&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;기대 : 양쪽 공백을 없앤다. (스페이스, 탭, 줄바꿈)&lt;/p&gt;
&lt;pre id=&quot;code_1726724381424&quot; class=&quot;cpp&quot; data-ke-language=&quot;cpp&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;        string strValue = &quot; \t  -25   \n&quot; ;
        printf(&quot;[%s]\n&quot;, strValue.c_str()) ;
        strValue = regex_replace(strValue, regex(&quot;^\\s*&quot;), &quot;&quot;) ;
        printf(&quot;[%s]\n&quot;, strValue.c_str()) ;
        strValue = regex_replace(strValue, regex(&quot;\\s*$&quot;), &quot;&quot;) ;
        printf(&quot;[%s]\n&quot;, strValue.c_str()) ;&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;결과 : [-25]&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/C,C++</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/328</guid>
      <comments>https://hahaite.tistory.com/328#entry328comment</comments>
      <pubDate>Thu, 19 Sep 2024 14:41:19 +0900</pubDate>
    </item>
    <item>
      <title>Android Studio 에서 Java 컴파일하기</title>
      <link>https://hahaite.tistory.com/327</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;도움받은 사이트 :&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;&lt;a href=&quot;https://daldalhanstory.tistory.com/105&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://daldalhanstory.tistory.com/105&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;한길 C++ 만 하다 대세가 대세인지라 안드로이드를 개발해야 한다. (주륵~ ㅠㅠ )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;기존 코드를 살펴보다 한계를 느껴 Java 를 처음부터 공부해보자 생각하고,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Android Studio 에서 Java 코드를 컴파일하는 방법을 정리한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;사실 리눅스에서 컴파일 + 실행하는 것이 훨씬 익숙하나&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;앞으로 Android Studio 를 계속 써야하기에 여러 방법을 찾아봤으나&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;오래된 Android Studio 이거나 따라했는데 안되거나 해서... 겨우 성공한 방법을 정리한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1. Android Studio 를 설치하고~&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. New Project 를 선택한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;997&quot; data-origin-height=&quot;157&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/lta4J/btsJz1z2Zct/D7YzynAarf13LLbQaT2841/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/lta4J/btsJz1z2Zct/D7YzynAarf13LLbQaT2841/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/lta4J/btsJz1z2Zct/D7YzynAarf13LLbQaT2841/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Flta4J%2FbtsJz1z2Zct%2FD7YzynAarf13LLbQaT2841%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;997&quot; height=&quot;157&quot; data-origin-width=&quot;997&quot; data-origin-height=&quot;157&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;3. No Activity 를 선택한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(사실 다른 것 선택해도 될 것 같은데, 확실히 No Activity 로 선택했다.)&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;682&quot; data-origin-height=&quot;330&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bb8J3d/btsJye2oZtr/o6pS3CsWX0nRgAR1iSvUdK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bb8J3d/btsJye2oZtr/o6pS3CsWX0nRgAR1iSvUdK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bb8J3d/btsJye2oZtr/o6pS3CsWX0nRgAR1iSvUdK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fbb8J3d%2FbtsJye2oZtr%2Fo6pS3CsWX0nRgAR1iSvUdK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;682&quot; height=&quot;330&quot; data-origin-width=&quot;682&quot; data-origin-height=&quot;330&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;4. 적당히 이름을 써주고 Language 는 Java 를 선택해 준다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;541&quot; data-origin-height=&quot;434&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bUGwAx/btsJz4wHSIx/TVTiIHrpDSpuq0k1pD7y7K/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bUGwAx/btsJz4wHSIx/TVTiIHrpDSpuq0k1pD7y7K/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bUGwAx/btsJz4wHSIx/TVTiIHrpDSpuq0k1pD7y7K/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbUGwAx%2FbtsJz4wHSIx%2FTVTiIHrpDSpuq0k1pD7y7K%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;541&quot; height=&quot;434&quot; data-origin-width=&quot;541&quot; data-origin-height=&quot;434&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;5. 프로젝트가 생성되면 java 우클릭 -&amp;gt; new -&amp;gt; Java Class 를 생성한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(&lt;b&gt;&lt;span style=&quot;color: #ee2323;&quot;&gt;app 이 아니다. java 에 생성해야 한다.&lt;/span&gt;&lt;/b&gt; -&amp;gt; 이것 때문에 계속 안됐음. ㅠㅠ )&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;692&quot; data-origin-height=&quot;238&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/c2g1Ok/btsJyCoqwwG/eQHKFIvhENKNgaKi5Y5LJK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/c2g1Ok/btsJyCoqwwG/eQHKFIvhENKNgaKi5Y5LJK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/c2g1Ok/btsJyCoqwwG/eQHKFIvhENKNgaKi5Y5LJK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fc2g1Ok%2FbtsJyCoqwwG%2FeQHKFIvhENKNgaKi5Y5LJK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;692&quot; height=&quot;238&quot; data-origin-width=&quot;692&quot; data-origin-height=&quot;238&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;6. 새 클래스를 생성하고 &quot;Hello, World~&quot; 출력하는 코드를 작성한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;477&quot; data-origin-height=&quot;158&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/zKTiE/btsJz6BhSgo/UI6Hu28PyYKB5umA7ahtl0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/zKTiE/btsJz6BhSgo/UI6Hu28PyYKB5umA7ahtl0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/zKTiE/btsJz6BhSgo/UI6Hu28PyYKB5umA7ahtl0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FzKTiE%2FbtsJz6BhSgo%2FUI6Hu28PyYKB5umA7ahtl0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;477&quot; height=&quot;158&quot; data-origin-width=&quot;477&quot; data-origin-height=&quot;158&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;7. 이제 컴파일 및 실행이 남았다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;코드 위에 마우스 우클릭 후, Run ~~ with Coverage 를 선택하면,&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;624&quot; data-origin-height=&quot;572&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cg8ZBL/btsJx28HdSg/3lPKTP6inzBvHhrqkJjK0K/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cg8ZBL/btsJx28HdSg/3lPKTP6inzBvHhrqkJjK0K/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cg8ZBL/btsJx28HdSg/3lPKTP6inzBvHhrqkJjK0K/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fcg8ZBL%2FbtsJx28HdSg%2F3lPKTP6inzBvHhrqkJjK0K%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;624&quot; height=&quot;572&quot; data-origin-width=&quot;624&quot; data-origin-height=&quot;572&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;8. 창 아래 결과가 출력된다. 끝. ㅠㅠ&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;552&quot; data-origin-height=&quot;207&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/x7VhM/btsJzetFNjF/XNJ8zhDy4kKzSZVfdyn9ak/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/x7VhM/btsJzetFNjF/XNJ8zhDy4kKzSZVfdyn9ak/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/x7VhM/btsJzetFNjF/XNJ8zhDy4kKzSZVfdyn9ak/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fx7VhM%2FbtsJzetFNjF%2FXNJ8zhDy4kKzSZVfdyn9ak%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;552&quot; height=&quot;207&quot; data-origin-width=&quot;552&quot; data-origin-height=&quot;207&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/잡동사니</category>
      <category>android studio</category>
      <category>android studio java 컴파일</category>
      <category>Java</category>
      <category>안드로이드 스튜디오</category>
      <category>자바</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/327</guid>
      <comments>https://hahaite.tistory.com/327#entry327comment</comments>
      <pubDate>Wed, 11 Sep 2024 20:04:04 +0900</pubDate>
    </item>
    <item>
      <title>Zebra ZPL 의 GFA 명령어 및 Bitmap 데이터 압축하기</title>
      <link>https://hahaite.tistory.com/326</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;도움받은 사이트 :&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://developer.zebra.com/thread/34694&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://developer.zebra.com/thread/34694&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://ashuro.tistory.com/20&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://ashuro.tistory.com/20&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://stackoverflow.com/questions/68627676/c-sharp-zebra-hex-compress-algorithm&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://stackoverflow.com/questions/68627676/c-sharp-zebra-hex-compress-algorithm&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Zebra ZPL 에서 GFA 명령어는 이미지를 라벨에 출력할 때 사용하는 Command 이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;labelary 사이트에서 간단히 가져다 쓸 수도 있지만&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;최대한 개념을 익히는 방향으로 글을 쓴다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&amp;clubs; BMP 파일 생성&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;테스트를 위해 BMP 파일을 하나 만든다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Zebra 프린터의 경우, 흑백으로 출력하기에 BMP 저장 시, 1비트로 저장한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래는 Paint.net (무료) 이라는 이미지툴에서 아래처럼 적당히 이미지를 만들고,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1비트로 저장하는 예시이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;디더링 수준은 테스트 결과, 무시해도 된다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;592&quot; data-origin-height=&quot;284&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cUWZD1/btsHeamRm2C/wu5X29jJC1Htv8PJWaEovk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cUWZD1/btsHeamRm2C/wu5X29jJC1Htv8PJWaEovk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cUWZD1/btsHeamRm2C/wu5X29jJC1Htv8PJWaEovk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcUWZD1%2FbtsHeamRm2C%2Fwu5X29jJC1Htv8PJWaEovk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;592&quot; height=&quot;284&quot; data-origin-width=&quot;592&quot; data-origin-height=&quot;284&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; Labelary 사이트에서 GFA 데이터 얻기&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1. Labelary 사이트에 접속한다. ( Link : &lt;a href=&quot;https://labelary.com/viewer.html&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://labelary.com/viewer.html&lt;/a&gt;&amp;nbsp; )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. 아래처럼 ZPL 코드창에 ^XA ^XZ 명령어를 입력한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;353&quot; data-origin-height=&quot;164&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/ocljl/btsHg7vGpSH/x5ivdMNGYe2HifdUK6Ndp1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/ocljl/btsHg7vGpSH/x5ivdMNGYe2HifdUK6Ndp1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/ocljl/btsHg7vGpSH/x5ivdMNGYe2HifdUK6Ndp1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Focljl%2FbtsHg7vGpSH%2Fx5ivdMNGYe2HifdUK6Ndp1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;353&quot; height=&quot;164&quot; data-origin-width=&quot;353&quot; data-origin-height=&quot;164&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;3. 위와 같이 커서를 두고, Add Image 버튼을 눌러 위에서 생성한 BMP 파일을 부르면,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래처럼 GFA 코드를 생성한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;546&quot; data-origin-height=&quot;298&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/mr91M/btsHcolQ0W6/4PP78JrFCc1mNvjrylkkE0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/mr91M/btsHcolQ0W6/4PP78JrFCc1mNvjrylkkE0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/mr91M/btsHcolQ0W6/4PP78JrFCc1mNvjrylkkE0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fmr91M%2FbtsHcolQ0W6%2F4PP78JrFCc1mNvjrylkkE0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;546&quot; height=&quot;298&quot; data-origin-width=&quot;546&quot; data-origin-height=&quot;298&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;4. 이제 위에 생성된 코드값을 적절히 사용하면 된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;5. 끝 ㅋㅋ~&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;6. 이제 나가세요. ㅎㅎ&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;실제 위와 같이 쓰는 경우도 봤지만 매번 저 사이트에서 이미지를 불러와 값을 얻어야 한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래는 위 값이 어떻게 얻어지는지에 대해 기술한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; BMP Color Table&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;BMP 정보에 Color Table 값이 있는데 이 값에 따라 0 -&amp;gt; 1 또는 1 -&amp;gt; 0 으로 변환시켜야 한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;예를 들어 아래와 같은 사각형은,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Color Table 값에 따라 역상되어 저장될 수 있다. 이 경우, 0 -&amp;gt; 1로 바꿔주는 작업이 필요하다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;435&quot; data-origin-height=&quot;320&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cdEXpC/btsHcIxCSDm/5SiBYfn7ZDY72P8f6sgGwK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cdEXpC/btsHcIxCSDm/5SiBYfn7ZDY72P8f6sgGwK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cdEXpC/btsHcIxCSDm/5SiBYfn7ZDY72P8f6sgGwK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcdEXpC%2FbtsHcIxCSDm%2F5SiBYfn7ZDY72P8f6sgGwK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;435&quot; height=&quot;320&quot; data-origin-width=&quot;435&quot; data-origin-height=&quot;320&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이게, 디자인팀으로부터 이미지를 받았을 때 역상되어 출력되어 우연히 발견한 경우인데,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;디자이너에게 물어봐도 자기도 모른다는 답변만...&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;일단은 무식하게, Color Table 값으로 위와 같이 두가지로 저장될 수 있다고 이해하자.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 1비트 BMP Raw Data&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;앞서 언급했듯이 비트 단위를 1비트로 두고 저장하면 실제 데이터는 비트 단위로 저장되게 된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;하지만 파일은 바이트 단위로 저장된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이에 비트 단위 데이터가 어떻게 저장되는지에 대한 이해가 필요하다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;예를 들어 6 x 5 크기의 bmp 파일이 있다고 하자.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 파일을 hex editor 로 열면 아래가 Data 영역이 된다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;918&quot; data-origin-height=&quot;290&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/LJsfW/btsHdwKAtkn/7JKrUi6EIOJokfScjGzGp0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/LJsfW/btsHdwKAtkn/7JKrUi6EIOJokfScjGzGp0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/LJsfW/btsHdwKAtkn/7JKrUi6EIOJokfScjGzGp0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FLJsfW%2FbtsHdwKAtkn%2F7JKrUi6EIOJokfScjGzGp0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;918&quot; height=&quot;290&quot; data-origin-width=&quot;918&quot; data-origin-height=&quot;290&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Raw Data 만 나열하면 아래와 같다. 높이가 5이니 5줄로 표시될 것이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(BMP Data 는 역행으로 저장되므로 맨 윗줄이 맨 아래 저장된다. 맨 아랫줄은 맨 위에 저장됨)&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;534&quot; data-origin-height=&quot;163&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/QZ1YJ/btsHcs2WO5n/fds0E3zdZX245u28yNu3P1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/QZ1YJ/btsHcs2WO5n/fds0E3zdZX245u28yNu3P1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/QZ1YJ/btsHcs2WO5n/fds0E3zdZX245u28yNu3P1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FQZ1YJ%2FbtsHcs2WO5n%2Ffds0E3zdZX245u28yNu3P1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;534&quot; height=&quot;163&quot; data-origin-width=&quot;534&quot; data-origin-height=&quot;163&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위에서 보는 것처럼 폭이 6 픽셀이지만 한줄은 32비트, 4바이트를 차지하고 26비트가 0으로 Padding 되었다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;만약 크기가 30&amp;nbsp; x 5 이면 어떨까?&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;한줄은 32비트 (4Bytes) 가 사용되며 우측 2비트는 Padding 되었다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;554&quot; data-origin-height=&quot;164&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/ouiCm/btsHb509Ln6/ENjsKW9i5yxUsDhICWjOGk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/ouiCm/btsHb509Ln6/ENjsKW9i5yxUsDhICWjOGk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/ouiCm/btsHb509Ln6/ENjsKW9i5yxUsDhICWjOGk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FouiCm%2FbtsHb509Ln6%2FENjsKW9i5yxUsDhICWjOGk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;554&quot; height=&quot;164&quot; data-origin-width=&quot;554&quot; data-origin-height=&quot;164&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이제 추측이 가능하다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이미지의 폭은 32비트 단위로 나뉘어지며 남는 비트는 0 으로 padding 되는 것을~&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이를 위해 38 x 5&amp;nbsp; 짜리의 Raw Data 를 확인해 보면 아래처럼 64비트, 8바이트로 확장됨을 확인할 수 있다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;151&quot; data-origin-height=&quot;113&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cLCYvq/btsHg4TjkGy/lITAQVnkKyDLzRO8CKbiz1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cLCYvq/btsHg4TjkGy/lITAQVnkKyDLzRO8CKbiz1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cLCYvq/btsHg4TjkGy/lITAQVnkKyDLzRO8CKbiz1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcLCYvq%2FbtsHg4TjkGy%2FlITAQVnkKyDLzRO8CKbiz1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;151&quot; height=&quot;113&quot; data-origin-width=&quot;151&quot; data-origin-height=&quot;113&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; GFA 값 생성&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;Zebra 문서에 따르면 GF Command 는 아래처럼 정의된다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;929&quot; data-origin-height=&quot;175&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cC2tRU/btsHcoTKMPE/5N53rPD4WFqrZfVZXlhrWk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cC2tRU/btsHcoTKMPE/5N53rPD4WFqrZfVZXlhrWk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cC2tRU/btsHcoTKMPE/5N53rPD4WFqrZfVZXlhrWk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcC2tRU%2FbtsHcoTKMPE%2F5N53rPD4WFqrZfVZXlhrWk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;929&quot; height=&quot;175&quot; data-origin-width=&quot;929&quot; data-origin-height=&quot;175&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;a : Compression Type&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp; &amp;nbsp; A : ASCII Hex 값. 위 예제처럼 Hex 텍스트로 읽을 수 있는 값. 우리가 사용하는 값&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp; &amp;nbsp; B : Binary - 말그대로 binary 그 자체. 메모장으로 열면 깨져서 보인다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp; &amp;nbsp; C : Compressed Binary - 위 binary 를 압축한 것 같다. 자세한 건 문서 참조.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;b : Binary byte count&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;c : Graphic field count&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;d : bytes per row&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;data : data&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 절에선 b,c,d 값 의 계산을 다룬다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;글 앞부분에서 Labelary 사이트에서 &quot;Add Image&quot; 로 bmp 파일을 불러오면&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;자동으로 GFA 코드가 생성되는 것을 확인할 수 있었다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;bmp 이미지 크기별로 생성되는 GFA 코드는 아래와 같다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(Data 영역은 나중에 다룰 것이며, 여기선 b,c,d 값에 중점을 둔다. )&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 91.3935%; height: 136px;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot; data-ke-style=&quot;style3&quot;&gt;
&lt;tbody&gt;
&lt;tr style=&quot;height: 34px;&quot;&gt;
&lt;td style=&quot;width: 17.4418%; height: 34px;&quot;&gt;이미지 크기 (Pixel)&lt;/td&gt;
&lt;td style=&quot;width: 14.6512%; text-align: center; height: 34px;&quot;&gt;^GFA 코드&lt;/td&gt;
&lt;td style=&quot;width: 19.4766%; text-align: center; height: 34px;&quot;&gt;b &lt;br /&gt;(Binary Byte Count)&lt;/td&gt;
&lt;td style=&quot;width: 21.8315%; text-align: center; height: 34px;&quot;&gt;c &lt;br /&gt;(Graphic Field Count)&lt;/td&gt;
&lt;td style=&quot;width: 17.8338%; text-align: center; height: 34px;&quot;&gt;d &lt;br /&gt;(bytes per row)&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 17.4418%; text-align: center; height: 17px;&quot;&gt;6 x 5&lt;/td&gt;
&lt;td style=&quot;width: 14.6512%; height: 17px; text-align: center;&quot;&gt;^GFA,5,5,1,&lt;/td&gt;
&lt;td style=&quot;width: 19.4766%; text-align: center; height: 17px;&quot;&gt;5&lt;/td&gt;
&lt;td style=&quot;width: 21.8315%; text-align: center; height: 17px;&quot;&gt;5&lt;/td&gt;
&lt;td style=&quot;width: 17.8338%; text-align: center; height: 17px;&quot;&gt;1&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 17.4418%; height: 17px; text-align: center;&quot;&gt;14 x 5&lt;/td&gt;
&lt;td style=&quot;width: 14.6512%; height: 17px; text-align: center;&quot;&gt;^GFA,10,10,2&lt;/td&gt;
&lt;td style=&quot;width: 19.4766%; height: 17px; text-align: center;&quot;&gt;10&lt;/td&gt;
&lt;td style=&quot;width: 21.8315%; height: 17px; text-align: center;&quot;&gt;10&lt;/td&gt;
&lt;td style=&quot;width: 17.8338%; height: 17px; text-align: center;&quot;&gt;2&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 17.4418%; height: 17px; text-align: center;&quot;&gt;22 x 5&lt;/td&gt;
&lt;td style=&quot;width: 14.6512%; height: 17px; text-align: center;&quot;&gt;^GFA,15,15,3&lt;/td&gt;
&lt;td style=&quot;width: 19.4766%; height: 17px; text-align: center;&quot;&gt;15&lt;/td&gt;
&lt;td style=&quot;width: 21.8315%; height: 17px; text-align: center;&quot;&gt;15&lt;/td&gt;
&lt;td style=&quot;width: 17.8338%; height: 17px; text-align: center;&quot;&gt;3&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 17.4418%; height: 17px; text-align: center;&quot;&gt;24 x 5&lt;/td&gt;
&lt;td style=&quot;width: 14.6512%; height: 17px; text-align: center;&quot;&gt;^GFA,15,15,3,&lt;/td&gt;
&lt;td style=&quot;width: 19.4766%; height: 17px; text-align: center;&quot;&gt;15&lt;/td&gt;
&lt;td style=&quot;width: 21.8315%; height: 17px; text-align: center;&quot;&gt;15&lt;/td&gt;
&lt;td style=&quot;width: 17.8338%; height: 17px; text-align: center;&quot;&gt;3&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 17.4418%; height: 17px; text-align: center;&quot;&gt;30 x 5&lt;/td&gt;
&lt;td style=&quot;width: 14.6512%; height: 17px; text-align: center;&quot;&gt;^GFA,20,20,4&lt;/td&gt;
&lt;td style=&quot;width: 19.4766%; height: 17px; text-align: center;&quot;&gt;20&lt;/td&gt;
&lt;td style=&quot;width: 21.8315%; height: 17px; text-align: center;&quot;&gt;20&lt;/td&gt;
&lt;td style=&quot;width: 17.8338%; height: 17px; text-align: center;&quot;&gt;4&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 17.4418%; height: 17px; text-align: center;&quot;&gt;38 x 5&lt;/td&gt;
&lt;td style=&quot;width: 14.6512%; height: 17px; text-align: center;&quot;&gt;^GFA,25,25,5&lt;/td&gt;
&lt;td style=&quot;width: 19.4766%; height: 17px; text-align: center;&quot;&gt;25&lt;/td&gt;
&lt;td style=&quot;width: 21.8315%; height: 17px; text-align: center;&quot;&gt;25&lt;/td&gt;
&lt;td style=&quot;width: 17.8338%; height: 17px; text-align: center;&quot;&gt;5&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;일단 눈대중으로 확인할 수 있는 내용은,&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;b,c 값을 동일하다. ( 아마도 GFB, GFC 인 경우, 두 값이 다를 것 같다.)&lt;/li&gt;
&lt;li&gt;d 값은 이미지의 폭을 8 로 나눈 몫이다. (int)width / 8&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그렇다면 b 값만 구하면 된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;우선, 이미지 폭 (width) 의 정의를 아래처럼 3가지로 나눌 수 있다. (용어는 내마음대로 정함)&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;799&quot; data-origin-height=&quot;406&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/k6YmU/btsHgnl7AFc/E5GGSwln3KIAKvY7iWEwc0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/k6YmU/btsHgnl7AFc/E5GGSwln3KIAKvY7iWEwc0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/k6YmU/btsHgnl7AFc/E5GGSwln3KIAKvY7iWEwc0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fk6YmU%2FbtsHgnl7AFc%2FE5GGSwln3KIAKvY7iWEwc0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;799&quot; height=&quot;406&quot; data-origin-width=&quot;799&quot; data-origin-height=&quot;406&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 때, b,d 값은&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;b = RealWidth * Rows = 1 * 5 = 5&lt;/li&gt;
&lt;li&gt;d = RealWidth = 1&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;가 된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;만약 30 x 5 픽셀이라면, 아래처럼 계산될 것이다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;825&quot; data-origin-height=&quot;388&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/b7CCNY/btsHhsmXuqo/YgeoMoCeMX7tcoKjSGLEF1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/b7CCNY/btsHhsmXuqo/YgeoMoCeMX7tcoKjSGLEF1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/b7CCNY/btsHhsmXuqo/YgeoMoCeMX7tcoKjSGLEF1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fb7CCNY%2FbtsHhsmXuqo%2FYgeoMoCeMX7tcoKjSGLEF1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;825&quot; height=&quot;388&quot; data-origin-width=&quot;825&quot; data-origin-height=&quot;388&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 때 b,d 값은&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;b = RealWidth * Rows = 4 * 5 = 20&lt;/li&gt;
&lt;li&gt;d = RealWidth = 4&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;가 된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; GFA 옵션 b,c,d 계산&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그림상으로는 위와 같이 계산이 되는데 실제 코드상에선&amp;nbsp; 아래처럼 구할 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;우선, BMP 헤더 구조체에서 구할 수 있는 정보는 아래와 같다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(아래 구조체 변수는 윈도우 기준이다.)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;BITMAPFILEHEADER bmFile ;&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;bmFile.bfSize : 파일 크기&lt;/li&gt;
&lt;li&gt;bmFile.bfOffBits : 파일에서 Raw Data 가 시작되는 위치&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;BITMAPINFOHEADER bmInfo ;&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;bmInfo.biWidth : 실제 이미지의 가로(폭) 사이즈&lt;/li&gt;
&lt;li&gt;bmInfo.biHeight : 실제 이미지의 세로(높이, rows) 사이즈&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 때, 앞절 그림의 4가지 값은 아래처럼 구할 수 있다.&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;bmInfo.biWidth = bmInfo.biWidth&lt;/li&gt;
&lt;li&gt;bmInfo.biHeight = bmInfo.biHeight&lt;/li&gt;
&lt;li&gt;Width = (bmFile.bfSize - bmFile.bfOffBits) /&amp;nbsp; bmInfo.biHeight&lt;/li&gt;
&lt;li&gt;RealWidth = (bmInfo.biWidth + 7) / 8&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이제 최종으로 GFA 명령어의 옵션 b,c,d 값은 아래처럼 계산된다.&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;b = RealWidth * bmInfo.biHeight&lt;/li&gt;
&lt;li&gt;c = b&lt;/li&gt;
&lt;li&gt;d = RealWidth&lt;/li&gt;
&lt;/ul&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; GFA 옵션 data 얻기 - 정상과 역상&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;앞서 언급했듯이 Color Table 에 따라 Raw Data 는 아래처럼 정상 또는 역상으로 저장되어 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;역상인 경우, 1-&amp;gt;0, 0-&amp;gt;1 로 뒤집어줘야 한다. (Exclusive OR )&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;524&quot; data-origin-height=&quot;305&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cvXkCc/btsHd7xQNG6/2KUHmWKUll4H29r15F8kB0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cvXkCc/btsHd7xQNG6/2KUHmWKUll4H29r15F8kB0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cvXkCc/btsHd7xQNG6/2KUHmWKUll4H29r15F8kB0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcvXkCc%2FbtsHd7xQNG6%2F2KUHmWKUll4H29r15F8kB0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;524&quot; height=&quot;305&quot; data-origin-width=&quot;524&quot; data-origin-height=&quot;305&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; GFA 옵션 data 얻기 - 정상&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래는 14 x 5 크기의 정상 Raw Data 영역이다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;757&quot; data-origin-height=&quot;303&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/lbphi/btsHgAMEuhw/lqBZCDFLsRccBCj9Fljsj1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/lbphi/btsHgAMEuhw/lqBZCDFLsRccBCj9Fljsj1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/lbphi/btsHgAMEuhw/lqBZCDFLsRccBCj9Fljsj1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Flbphi%2FbtsHgAMEuhw%2FlqBZCDFLsRccBCj9Fljsj1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;757&quot; height=&quot;303&quot; data-origin-width=&quot;757&quot; data-origin-height=&quot;303&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위의 경우, Real Width = 2 Bytes 만큼만 취하고 나머지는 버린다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;크기가 14 이므로 16 - 14 = 2 bits 만큼 0 으로 채운다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 남은 데이터가 GFA 의 마지막 data 옵션에 들어간다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위 그림의 경우,&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;FFFCC38472E41A3C0E0C&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;가 최종 data 가 된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 data 만으로도 이미지를 출력할 수 있지만 압축하여 data 의 길이를 줄일 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이는 저~ 아래에서 다룬다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위 데이터값을 사용하여 아래와 같이 ZPL 을 구성할 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Labelary 에서 정상적으로 bitmap 을 출력하는 것을 확인할 수 있다.&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 100%;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%; text-align: center;&quot;&gt;ZPL&lt;/td&gt;
&lt;td style=&quot;width: 50%; text-align: center;&quot;&gt;라벨 이미지&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;^XA&lt;br /&gt;^FO10,10&lt;br /&gt;^GFA,10,10,2,FFFCC38472E41A3C0E0C&lt;br /&gt;^XZ&lt;/td&gt;
&lt;td style=&quot;width: 50%;&quot;&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;197&quot; data-origin-height=&quot;116&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/dwdYaI/btsHd93zAIg/Hiwvlba1bEFcXf1flgvCwK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/dwdYaI/btsHd93zAIg/Hiwvlba1bEFcXf1flgvCwK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/dwdYaI/btsHd93zAIg/Hiwvlba1bEFcXf1flgvCwK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FdwdYaI%2FbtsHd93zAIg%2FHiwvlba1bEFcXf1flgvCwK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;197&quot; height=&quot;116&quot; data-origin-width=&quot;197&quot; data-origin-height=&quot;116&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; GFA 옵션 data 얻기 - 역상&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위 이미지의 역상 Raw Data는 아래와 같다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;정상인 경우와 마찬가지로 우측 2 Bytes 를 버린다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;그리고 정상과는 달리 1로 Padding bits 를 채운다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;718&quot; data-origin-height=&quot;280&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/ctzgmb/btsHhR8fDXX/4RljknkKSm9jy1itnYy3sk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/ctzgmb/btsHhR8fDXX/4RljknkKSm9jy1itnYy3sk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/ctzgmb/btsHhR8fDXX/4RljknkKSm9jy1itnYy3sk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fctzgmb%2FbtsHhR8fDXX%2F4RljknkKSm9jy1itnYy3sk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;718&quot; height=&quot;280&quot; data-origin-width=&quot;718&quot; data-origin-height=&quot;280&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;데이터 버리고 Padding Bits 를 1로 채우면 아래와 같다.&lt;br /&gt;그리고 Exclusive OR (XOR) 연산을 하면 정상과 같은 데이터를 얻을 수 있다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;482&quot; data-origin-height=&quot;368&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/saTW3/btsHi5xV0W7/zom1Kpp6kKEjgGrLvlE2s1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/saTW3/btsHi5xV0W7/zom1Kpp6kKEjgGrLvlE2s1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/saTW3/btsHi5xV0W7/zom1Kpp6kKEjgGrLvlE2s1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FsaTW3%2FbtsHi5xV0W7%2Fzom1Kpp6kKEjgGrLvlE2s1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;482&quot; height=&quot;368&quot; data-origin-width=&quot;482&quot; data-origin-height=&quot;368&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 후, 정상과 같은 절차로 GFA 를 생성할 수 있다. (정상과 같으므로 생략)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; Raw Data 압축&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;테스트를 위해 아래와 같이 임의의 1bits 짜리 bmp 파일을 생성했다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;692&quot; data-origin-height=&quot;261&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/boeBUi/btsHj1oC8VQ/zxu77xmvZaAilzQgdXY1uk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/boeBUi/btsHj1oC8VQ/zxu77xmvZaAilzQgdXY1uk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/boeBUi/btsHj1oC8VQ/zxu77xmvZaAilzQgdXY1uk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FboeBUi%2FbtsHj1oC8VQ%2Fzxu77xmvZaAilzQgdXY1uk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;692&quot; height=&quot;261&quot; data-origin-width=&quot;692&quot; data-origin-height=&quot;261&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 위 절차와 같이 GFA 명령어용 data 를 추출하면 아래와 같다.&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;AAAEE000AAAEE000AAAEE0000000000000000000FC3FE78087E73C00&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그런데 위 이미지 파일을 labelary 사이트에서 불러오면 data 영역이 아래와 같다.&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;IAEE,::,:FC3FE78,87E73C,&lt;/li&gt;
&lt;/ul&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;두 결과는 같다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;즉, 위 56글자를 아래 24글자로 줄일 수 있다는 것이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;규칙은 아래와 같다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;■ 연속된 글자&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;연속된 글자는 &quot;갯수 + 글자&quot; 로 줄인다. 예를 들면,&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 56.2772%; height: 81px;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot; data-ke-style=&quot;style2&quot;&gt;
&lt;tbody&gt;
&lt;tr style=&quot;height: 20px;&quot;&gt;
&lt;td style=&quot;width: 17.8435%; text-align: center; height: 20px;&quot;&gt;Raw Data&lt;/td&gt;
&lt;td style=&quot;width: 13.4505%; text-align: center; height: 20px;&quot;&gt;압축&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%; text-align: center; height: 20px;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 20px;&quot;&gt;
&lt;td style=&quot;width: 17.8435%; text-align: center; height: 20px;&quot;&gt;444444&lt;/td&gt;
&lt;td style=&quot;width: 13.4505%; text-align: center; height: 20px;&quot;&gt;L4&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%; height: 20px;&quot;&gt;L=6번 반복 -&amp;gt; 4를 6번 찍음&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 24px;&quot;&gt;
&lt;td style=&quot;width: 17.8435%; text-align: center; height: 24px;&quot;&gt;DDD&lt;/td&gt;
&lt;td style=&quot;width: 13.4505%; text-align: center; height: 24px;&quot;&gt;ID&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%; height: 24px;&quot;&gt;I=3번 반복 -&amp;gt; D를 3번 찍음&lt;/td&gt;
&lt;/tr&gt;
&lt;tr style=&quot;height: 17px;&quot;&gt;
&lt;td style=&quot;width: 17.8435%; text-align: center; height: 17px;&quot;&gt;C -&amp;gt; 340 개 연속&lt;/td&gt;
&lt;td style=&quot;width: 13.4505%; text-align: center; height: 17px;&quot;&gt;wC&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%; height: 17px;&quot;&gt;w=340번 반복&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 17.8435%; text-align: center;&quot;&gt;C -&amp;gt; 342개&lt;/td&gt;
&lt;td style=&quot;width: 13.4505%; text-align: center;&quot;&gt;wHC&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%;&quot;&gt;w=340번 + H=2번 만큼 반복&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 17.8435%; text-align: center;&quot;&gt;F -&amp;gt; 495개&lt;/td&gt;
&lt;td style=&quot;width: 13.4505%; text-align: center;&quot;&gt;zFjUF&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%;&quot;&gt;z(400) + j (80) + U (15)&amp;nbsp; = 495 개&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;반복 횟수를 나타내는 앞글자는 아래처럼 정의된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;HEX 값에 사용되는 A~F 를 벗어난 값으로 세팅됨을 알 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;G, H 의 경우, 20회 이상인 경우에 사용된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;반복횟수가 1인 경우 -&amp;gt; 압축하면 손해 (1글자 -&amp;gt; 2글자)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;반복횟수가 2인경우 -&amp;gt; 압축의 의미없음 (2글자 -&amp;gt; 2글자)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;400개 이상인 경우, 400개에서 끊는다.&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 51.6279%; height: 200px;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr style=&quot;height: 155px;&quot;&gt;
&lt;td style=&quot;width: 18.0233%; height: 155px;&quot;&gt;G : 1 회 (20회 이상)&lt;br /&gt;H : 2 회 (20회 이상)&lt;br /&gt;I : 3 회&lt;br /&gt;J : 4 회&lt;br /&gt;K : 5&lt;br /&gt;L : 6&lt;br /&gt;M : 7&lt;br /&gt;N : 8&lt;br /&gt;O : 9&lt;br /&gt;P : 10&lt;br /&gt;&lt;br /&gt;&lt;/td&gt;
&lt;td style=&quot;width: 11.7441%; height: 155px;&quot;&gt;Q : 11 회&lt;br /&gt;R : 12 회&lt;br /&gt;S : 13 회&lt;br /&gt;T : 14&lt;br /&gt;U : 15&lt;br /&gt;V : 16&lt;br /&gt;W : 17&lt;br /&gt;X : 18&lt;br /&gt;Y : 19&lt;/td&gt;
&lt;td style=&quot;width: 10.5814%; height: 155px;&quot;&gt;g : 20회&lt;br /&gt;h : 40회&lt;br /&gt;i : 60회&lt;br /&gt;j : 80회&lt;br /&gt;k : 100&lt;br /&gt;l : 120&lt;br /&gt;m : 140&lt;br /&gt;n : 160&lt;br /&gt;o : 180&lt;br /&gt;p : 200&lt;/td&gt;
&lt;td style=&quot;width: 11.2791%; height: 155px;&quot;&gt;q : 220 회&lt;br /&gt;r : 240&lt;br /&gt;s : 260&lt;br /&gt;t : 280&lt;br /&gt;u : 300&lt;br /&gt;v : 320&lt;br /&gt;w : 340&lt;br /&gt;x : 360&lt;br /&gt;y : 380&lt;br /&gt;z : 400&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;■ 한 줄 끝까지 0인 경우,&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;예를 들어 Data의 뒷부분이 0 이면 ,(콤마) 로 치환할 수 있다.&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 56.2772%;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot; data-ke-style=&quot;style3&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 12.4716%; text-align: center;&quot;&gt;Raw Data&lt;/td&gt;
&lt;td style=&quot;width: 18.8224%; text-align: center;&quot;&gt;압축&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%; text-align: center;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 12.4716%; text-align: center;&quot;&gt;DA0000&lt;/td&gt;
&lt;td style=&quot;width: 18.8224%; text-align: center;&quot;&gt;DA,&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%;&quot;&gt;&amp;nbsp;&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 12.4716%; text-align: center;&quot;&gt;000000&lt;/td&gt;
&lt;td style=&quot;width: 18.8224%; text-align: center;&quot;&gt;,&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%;&quot;&gt;한줄 전체가 ',' 로 압축됨&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 12.4716%; text-align: center;&quot;&gt;555F00&lt;/td&gt;
&lt;td style=&quot;width: 18.8224%; text-align: center;&quot;&gt;I5F,&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%;&quot;&gt;5 세번 + 'F' + ','&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;■ 한 줄 끝까지 F인 경우,&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위와 맥락이 같으며 뒷부분이 F이면, ! (느낌표) 로 치환할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;내용은 위 0 과 동일하다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&lt;span style=&quot;text-align: start;&quot;&gt;■ 윗 줄과 같은 경우&lt;/span&gt;&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span&gt;윗줄과 내용이 같으면 : (콜론) 으로 치환할 수 있다.&lt;/span&gt;&lt;span&gt;&amp;nbsp;&lt;/span&gt;&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 56.2772%;&quot; border=&quot;1&quot; data-ke-style=&quot;style3&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 12.4716%;&quot;&gt;Raw Data&lt;/td&gt;
&lt;td style=&quot;width: 18.8224%;&quot;&gt;압축&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%;&quot;&gt;설명&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 12.4716%;&quot;&gt;DA0000&lt;br /&gt;DA0000&lt;/td&gt;
&lt;td style=&quot;width: 18.8224%;&quot;&gt;&lt;b&gt;DA,:&lt;/b&gt;&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%;&quot;&gt;두번째 줄이 윗줄과 같으므로 ':' 으로 압축됨&lt;/td&gt;
&lt;/tr&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 12.4716%;&quot;&gt;DA0000&lt;br /&gt;DA0000&lt;br /&gt;DA0000&lt;br /&gt;DA0000&lt;/td&gt;
&lt;td style=&quot;width: 18.8224%;&quot;&gt;&lt;b&gt;DA,:::&lt;/b&gt;&lt;/td&gt;
&lt;td style=&quot;width: 35.4169%;&quot;&gt;뒤에 세줄 반복이므로&lt;br /&gt;':' 를 세번 사용하여 표시함.&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위와 같이 압축기법을 적용하면, 위 25x7 예제 BMP 파일의 raw data 는 아래처럼 압축될 것이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;최종으로 얻은 값은 Labelary 사이트에서 생성된 값이랑 일치함을 확인할 수 있다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;488&quot; data-origin-height=&quot;487&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/b0cNFv/btsHitmcI3b/pjLD7ll8DjafATK4Rkzc21/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/b0cNFv/btsHitmcI3b/pjLD7ll8DjafATK4Rkzc21/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/b0cNFv/btsHitmcI3b/pjLD7ll8DjafATK4Rkzc21/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fb0cNFv%2FbtsHitmcI3b%2FpjLD7ll8DjafATK4Rkzc21%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;488&quot; height=&quot;487&quot; data-origin-width=&quot;488&quot; data-origin-height=&quot;487&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;clubs; BMP 파일 생성&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;테스트를 위해 BMP 파일을 하나 만든다.&lt;/p&gt;
&lt;ul style=&quot;list-style-type: disc;&quot; data-ke-list-type=&quot;disc&quot;&gt;
&lt;li&gt;Visual Studio 2017 Express&lt;/li&gt;
&lt;li&gt;Windows API 기반 C++&lt;/li&gt;
&lt;li&gt;콘솔 환경에서 컴파일하여 결과를 얻을 수 있다.&lt;/li&gt;
&lt;li&gt;main() 함수에서 test.bmp 를 본인의 파일로 적절히 수정한다.&lt;/li&gt;
&lt;/ul&gt;
&lt;pre id=&quot;code_1715567890264&quot; class=&quot;cpp&quot; data-ke-language=&quot;cpp&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;#include &amp;lt;cstdio&amp;gt;
#include &amp;lt;string&amp;gt;

#include &amp;lt;list&amp;gt;
#include &amp;lt;map&amp;gt;

#include &amp;lt;windows.h&amp;gt;

using namespace std ;

int compressData(list&amp;lt;string&amp;gt;* pList)
{
	list&amp;lt;string&amp;gt;::iterator pListIter ;	
	list&amp;lt;string&amp;gt;::iterator pListIter2 ;	

	pListIter2 = pList-&amp;gt;end() ;
	int flagFirst = 1 ;

	// check data is same as above line
	if(pList-&amp;gt;size() &amp;gt; 1)
	{
		while(1)
		{
			pListIter2-- ;
			pListIter = pListIter2 ;
			pListIter-- ;

			if(!pListIter-&amp;gt;compare(*pListIter2))
				*pListIter2 = &quot;:&quot; ;

			if(pListIter == pList-&amp;gt;begin())
				break ;
		}
	}

	// Check last data &quot;0&quot;
	size_t pos ;
	int p ;
	for(auto&amp;amp; zpl : *pList)
	{
		pos = zpl.find_last_not_of(&quot;0&quot;) ;

		// Skip if the last character is not &quot;0&quot;
		if(zpl.back() != '0')
			continue ;

		p = (pos == string::npos) ? -1 : pos ;
		zpl.replace(zpl.begin()+(p+1), zpl.end(), &quot;,&quot;) ;
	}

	// Check last data &quot;F&quot;
	for(auto&amp;amp; zpl : *pList)
	{
		pos = zpl.find_last_not_of(&quot;F&quot;) ;

		// Skip if the last character is not &quot;0&quot;
		if(zpl.back() != 'F')
			continue ;

		p = (pos == string::npos) ? -1 : pos ;
		zpl.replace(zpl.begin()+(p+1), zpl.end(), &quot;!&quot;) ;
	}

	// check ducplicated character.
	list&amp;lt;pair&amp;lt;char, int&amp;gt; &amp;gt; 			listCount ;
	list&amp;lt;pair&amp;lt;char, int&amp;gt; &amp;gt;::iterator 	listCountIter ;
	int len, cnt ;
	char prev, cur ;

	for(auto&amp;amp; zpl : *pList)
	{
		string strOrg = zpl ;
		len = zpl.length() ;
		prev = 0;
		cnt = 0 ;
		listCount.clear() ;
		for(int ii = 0; ii &amp;lt; len; ii++)
		{
			cur = zpl[ii] ;

			if(cur == prev)
			{
				cnt++ ;
			}
			else 	// cur != prev
			{
				if(prev)
					listCount.push_back(make_pair(prev, cnt)) ;
				cnt = 1 ;
				prev = cur ;
			}

			if(cnt == 400)
			{
				listCount.push_back(make_pair(cur, 400)) ;
				cnt = 0 ;
			}

			if(ii == len-1 &amp;amp;&amp;amp; cnt &amp;gt; 0 )
				listCount.push_back(make_pair(cur, cnt)) ;

		}

//		printf(&quot;======= List Count ======\n&quot;) ;
		int quotient, remainder ;

		zpl.clear() ;
		char ch1, ch20;
		for(auto data : listCount)
		{
//			printf(&quot;%c - %d\n&quot;, data.first, data.second) ;

			if(data.second &amp;lt;= 2)
			{
				zpl += data.first ;
				if(data.second == 2)
					zpl += data.first ;
				continue ;
			}

			// 3 &amp;lt;= data.second &amp;lt;= 19
			if(data.second &amp;lt; 20)
			{
				ch1 = 'G' + data.second - 1 ;
				zpl += ch1 ;
				zpl += data.first ;
				continue ;
			}

			// 20 &amp;lt;= data.second &amp;lt;= 400
			quotient = (int)data.second/20 ;
			remainder = data.second % 20 ;

			ch1 = (remainder &amp;gt; 0) ? 'G' + remainder - 1 : '0' ;
			ch20 = 'g' + quotient - 1 ;

			zpl += ch20 ;
			if(remainder &amp;gt; 0)
				zpl += ch1 ;	

			zpl += data.first ;
		}

//		printf(&quot;ORG : %s\n&quot;, strOrg.c_str()) ;
//		printf(&quot;NEW : %s\n&quot;, zpl.c_str()) ;
	}

	return 1 ;
}

string genZPL_Bitmap(const char* szFile)
{
	BITMAPFILEHEADER bmFile ;
	BITMAPINFOHEADER bmInfo ;
	unsigned char colorTable[4]  ;

	int flagInvert=0 ;
	char szText[1024] ;

	string strZpl ;

	strZpl = &quot;^XA&quot; ;
	strZpl += &quot;^FO20,20&quot; ;

	sprintf(szText, &quot;./%s&quot;, szFile) ;
	FILE* fp = fopen(szText, &quot;rb&quot;) ;

	if(!fp)
	{
		printf(&quot;genBitmap File Error - %s\n&quot;, szText) ;
		strZpl.clear() ;
		return strZpl ;
	}

	fread(&amp;amp;bmFile, sizeof(BITMAPFILEHEADER), 1, fp) ;
	fread(&amp;amp;bmInfo, sizeof(BITMAPINFOHEADER), 1, fp) ;
	fread(colorTable, sizeof(colorTable), 1, fp) ;

	printf(&quot;File : %s\n&quot;, szFile) ;
	printf(&quot;bmFile.bfSize : %d\n&quot;, bmFile.bfSize) ;
	printf(&quot;bmFile.biWidth : %d\n&quot;, bmInfo.biWidth) ;
	printf(&quot;bmFile.biHeight: %d\n&quot;, bmInfo.biHeight) ;

	printf(&quot;ColorTable : %02X %02X %02X %02X\r\n&quot;,
		colorTable[0], colorTable[1], colorTable[2], colorTable[3]) ;

	if(colorTable[0] * colorTable[1] * colorTable[2] &amp;lt; 0x800000)
		flagInvert = 1 ;

	printf(&quot;FlagInvert = %d\r\n&quot;, flagInvert) ;

	fseek(fp, bmFile.bfOffBits, SEEK_SET) ;

	printf(&quot;bmFile.bfOffBits = %d (0x%02X)\r\n&quot;, bmFile.bfOffBits, bmFile.bfOffBits &amp;amp; 0xff) ;
	printf(&quot;bmInfo.Width = %d\r\n&quot;, bmInfo.biWidth) ;

	int width = (bmFile.bfSize - bmFile.bfOffBits)/bmInfo.biHeight ;
	int realWidthByte = (bmInfo.biWidth + 7) / 8 ;
	
	printf(&quot;Width ; %d\r\n&quot;, width) ;
	printf(&quot;Real Width Byte; %d\r\n&quot;, realWidthByte) ;

	int imageSize = realWidthByte * bmInfo.biHeight ;
	printf(&quot;GFA Image Count : %d\r\n&quot;, imageSize ) ;

	sprintf(szText, &quot;^GFA,%d,%d,%d,&quot;, imageSize, imageSize, realWidthByte) ;
	strZpl += szText ;

	list&amp;lt;string&amp;gt; 		listRow ;
	list&amp;lt;string&amp;gt;::iterator 	listRowIter ;

	string strRow ;
	char szTemp[32] ;
	int nTemp ;
	unsigned char shValue ;

	for(int ii = 0; ii &amp;lt; bmInfo.biHeight; ii++)
	{
		strRow.clear() ;
		for(int jj = 1; jj &amp;lt;= width; jj++)
		{
			fread(szTemp, 1, 1, fp) ;

			if(jj &amp;gt; realWidthByte)
				continue ;

			if(jj == realWidthByte)
			{
				nTemp = bmInfo.biWidth &amp;amp; 0x07 ;
				shValue = 0xff ; // case of flagInvert == 1 72x72
				shValue = (nTemp == 1) ? 0x80 : shValue ;
				shValue = (nTemp == 2) ? 0xC0 : shValue ;
				shValue = (nTemp == 3) ? 0xE0 : shValue ;
				shValue = (nTemp == 4) ? 0xF0 : shValue ;
				shValue = (nTemp == 5) ? 0xF8 : shValue ;
				shValue = (nTemp == 6) ? 0xFC : shValue ;
				shValue = (nTemp == 7) ? 0xFE : shValue ;

				if(flagInvert)
					szTemp[0] |= (shValue ^ 0xff) ;
				else
					szTemp[0] &amp;amp;= shValue ;
			}

			if(flagInvert)
				szTemp[0] ^= 0xff ;

			szTemp[1] = '\0' ;
			sprintf(szText, &quot;%02X&quot;, szTemp[0] &amp;amp; 0xff) ;
			strRow += szText ;
		}

		listRow.push_front(strRow) ;
	}
	fclose(fp) ;

#if 1
	// compress Data
	printf(&quot;********** Before compress data **********\n&quot;) ;
	for(auto&amp;amp; pData : listRow)
		printf(&quot;%s\n&quot;, pData.c_str()) ;

	compressData(&amp;amp;listRow) ;

	printf(&quot;********** Aftercompress data **********\n&quot;) ;
	for(auto&amp;amp; pData : listRow)
		printf(&quot;%s\n&quot;, pData.c_str()) ;
#endif

	// Add Raw Data
	listRowIter = listRow.begin() ;
	for(; listRowIter != listRow.end(); listRowIter++)
		strZpl += *listRowIter ;

	strZpl += &quot;^FS&quot;;
	strZpl += &quot;^XZ&quot;;

	return strZpl ;
}

int main()
{
	string strZpl ;

	const char* szFile = &quot;./test.bmp&quot; ;
	strZpl = genZPL_Bitmap(szFile) ;

	printf(&quot;ZPL : %s\n&quot;, strZpl.c_str()) ;

#if 1
	// copy ZPL to ClipBoard
	if(!OpenClipboard(NULL))
	{
		printf(&quot;Failed OpenClipboard()\r\n&quot;) ;
		return 1;
	}

	if(!EmptyClipboard())
	{
		printf(&quot;Failed EmptyClipboard()\r\n&quot;) ;
		return 1 ;
	}

	int len = strZpl.length() ;
	HGLOBAL hGlobal = GlobalAlloc(GMEM_MOVEABLE, len + 1) ;
	char* pClip = (char*)GlobalLock(hGlobal) ;
	strcpy(pClip, strZpl.c_str()) ;
	GlobalUnlock(hGlobal) ;

	if(!SetClipboardData(CF_TEXT, hGlobal))
	{
		printf(&quot;Failed SetClipboardData()\r\n&quot;) ;
	}

	CloseClipboard() ;
#endif

	return 1 ;
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/잡동사니</category>
      <category>gf bitmap</category>
      <category>gfa</category>
      <category>gfa bitmap</category>
      <category>zebra bitmap</category>
      <category>zpl</category>
      <category>zpl gf</category>
      <category>zpl gfa</category>
      <category>제브라 비트맵</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/326</guid>
      <comments>https://hahaite.tistory.com/326#entry326comment</comments>
      <pubDate>Mon, 13 May 2024 11:47:19 +0900</pubDate>
    </item>
    <item>
      <title>VS Code 에서 Linux에 원격접속하여 컴파일하기</title>
      <link>https://hahaite.tistory.com/325</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;도움받은 사이트 :&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://code.visualstudio.com/docs/remote/ssh&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://code.visualstudio.com/docs/remote/ssh&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;난 VirtualBox 로 Ubuntu Server 를 설치하고,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;윈도우에서 putty 로 위 Ubuntu 에 SSH 로 접속하여 컴파일하는 것을 선호한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;치명적인 단점은 Break Point 걸어서 디버깅하는 것이 Visual Studio 의 그것보다 못하다는 것이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;뭐, Ubuntu Desktop 깔아서 여러 디버깅 툴(ddd 등) 을 깔아 써도 되지만&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이것 때문에 가볍게 돌아가는 Ubuntu Server 를 포기하기엔 아까웠다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;윈도우에 MinGW 설치해 요래요래 하는 방법도 많던데, 뭔가 발전이 없어보여 안함.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;( gcc 최신버전이 11.4 인데 MinGW 는 8.x 라든지... )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그래서 찾아보니, Visual Studio Code 에서 원격으로 접속해서 컴파일 및 디버깅까지&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;가능하다고 한다. 헐~&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이에 아래처럼 정리한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(이 글 읽을 정도면 개발 초중급 이상은 되리라 보기에 VS code 설치 쪽에 중심을 두고 정리한다.)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;1. Ubuntu Server 를 실행한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;2. Visual Studio Code 를 설치한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;3. VS Code 에서 Remote-SSH Extensions 을 설치한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;786&quot; data-origin-height=&quot;442&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/dfgGab/btsFBLiLaxR/Zg4V9zex8pkNSgn9iuVGT0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/dfgGab/btsFBLiLaxR/Zg4V9zex8pkNSgn9iuVGT0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/dfgGab/btsFBLiLaxR/Zg4V9zex8pkNSgn9iuVGT0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FdfgGab%2FbtsFBLiLaxR%2FZg4V9zex8pkNSgn9iuVGT0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;786&quot; height=&quot;442&quot; data-origin-width=&quot;786&quot; data-origin-height=&quot;442&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;4. VS Code 에서 F1 키를 눌러 아래창이 뜨면, &quot;Remote-SSH : Connected to Host&quot; 를 선택한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;462&quot; data-origin-height=&quot;168&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/blHWKB/btsFB8rdC8t/21uDgl7QQfkbGyk1Gkv9k0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/blHWKB/btsFB8rdC8t/21uDgl7QQfkbGyk1Gkv9k0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/blHWKB/btsFB8rdC8t/21uDgl7QQfkbGyk1Gkv9k0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FblHWKB%2FbtsFB8rdC8t%2F21uDgl7QQfkbGyk1Gkv9k0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;462&quot; height=&quot;168&quot; data-origin-width=&quot;462&quot; data-origin-height=&quot;168&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;5. 아래처럼 Select configured SSH host or enter user@host 라고 뜨면,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래 창에 접속할 id 와 호스트(IP) 를 입력한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;나같은 경우, hahaite@192.168.56.2 이다.&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;660&quot; data-origin-height=&quot;110&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/nuXR0/btsFFPKeZDq/CxLkD3WbNvolgqVuyYKxY0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/nuXR0/btsFFPKeZDq/CxLkD3WbNvolgqVuyYKxY0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/nuXR0/btsFFPKeZDq/CxLkD3WbNvolgqVuyYKxY0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FnuXR0%2FbtsFFPKeZDq%2FCxLkD3WbNvolgqVuyYKxY0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;660&quot; height=&quot;110&quot; data-origin-width=&quot;660&quot; data-origin-height=&quot;110&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;6. 그러면 아래처럼 새 창이 뜨면서 Enter password for hahaite@192.168.56.2 라고 뜬다. password 를 입력해 준다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;623&quot; data-origin-height=&quot;124&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bY1oCp/btsFEgBOMHD/bNPv1An6hZnd5Ch7OIlWT1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bY1oCp/btsFEgBOMHD/bNPv1An6hZnd5Ch7OIlWT1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bY1oCp/btsFEgBOMHD/bNPv1An6hZnd5Ch7OIlWT1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbY1oCp%2FbtsFEgBOMHD%2FbNPv1An6hZnd5Ch7OIlWT1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;623&quot; height=&quot;124&quot; data-origin-width=&quot;623&quot; data-origin-height=&quot;124&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;7. Ubuntu 에 VS Code Server 설치 (자동설치임)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위와 같이 password 를 입력하면 우측 하단에 VS Code server 인가를 세팅 중이라고 안내문구가 뜬다. (스샷 못찍음 ㅠㅠ )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;설치가 완료되고 정상적으로 연결이 되면, 촤측 하단에 아래처럼 SSH : IP 가 뜬다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;292&quot; data-origin-height=&quot;126&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/dxFcKv/btsFD6Tu3Ub/0OE6kfqY3GTzL13kOCOKL0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/dxFcKv/btsFD6Tu3Ub/0OE6kfqY3GTzL13kOCOKL0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/dxFcKv/btsFD6Tu3Ub/0OE6kfqY3GTzL13kOCOKL0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FdxFcKv%2FbtsFD6Tu3Ub%2F0OE6kfqY3GTzL13kOCOKL0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;292&quot; height=&quot;126&quot; data-origin-width=&quot;292&quot; data-origin-height=&quot;126&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 때, Ubuntu 에서 ps -ef 명령어로 실행 중인 프로세스를 확인해 보면 아래처럼 vscode-server 라고 뭔가 떠있는게 보인다. 이는 윈도우의 vs code 에서 자동으로 설치해 준 것이다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;473&quot; data-origin-height=&quot;136&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/eny4kx/btsFBMPvhEv/WUyL1qE5ozNGjCMEjr3rS0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/eny4kx/btsFBMPvhEv/WUyL1qE5ozNGjCMEjr3rS0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/eny4kx/btsFBMPvhEv/WUyL1qE5ozNGjCMEjr3rS0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Feny4kx%2FbtsFBMPvhEv%2FWUyL1qE5ozNGjCMEjr3rS0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;473&quot; height=&quot;136&quot; data-origin-width=&quot;473&quot; data-origin-height=&quot;136&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;8. 설치&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이제 File -&amp;gt; Open File 해보면 접속된 Ubuntu 의 디렉토리가 보인다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아무 파일이나 열고 Run and Debug 아이콘을 클릭하고 Run and Debug 를 클릭한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;732&quot; data-origin-height=&quot;288&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cHGeWg/btsFEZGokzK/kyJbNXeFNFpBz2biqA0UHk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cHGeWg/btsFEZGokzK/kyJbNXeFNFpBz2biqA0UHk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cHGeWg/btsFEZGokzK/kyJbNXeFNFpBz2biqA0UHk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcHGeWg%2FbtsFEZGokzK%2FkyJbNXeFNFpBz2biqA0UHk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;732&quot; height=&quot;288&quot; data-origin-width=&quot;732&quot; data-origin-height=&quot;288&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래처럼 뜨면 Install an extension for C++ 을 선택해 준다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;739&quot; data-origin-height=&quot;223&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/ez6dHC/btsFFmhiMls/5At6wdNw3RWc1dP0lcaFU1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/ez6dHC/btsFFmhiMls/5At6wdNw3RWc1dP0lcaFU1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/ez6dHC/btsFFmhiMls/5At6wdNw3RWc1dP0lcaFU1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fez6dHC%2FbtsFFmhiMls%2F5At6wdNw3RWc1dP0lcaFU1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;739&quot; height=&quot;223&quot; data-origin-width=&quot;739&quot; data-origin-height=&quot;223&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 아래처럼 C/C++ IntelliSense, debugging 등을 설치해 준다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래는 최초 한번만 설치해 주는 것이며, Ubuntu Server 에 원격으로 설치되는 것으로 보인다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;594&quot; data-origin-height=&quot;249&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/k2p8l/btsFD5tyOSV/oHwHkcSiGoZaCIeXdkubdk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/k2p8l/btsFD5tyOSV/oHwHkcSiGoZaCIeXdkubdk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/k2p8l/btsFD5tyOSV/oHwHkcSiGoZaCIeXdkubdk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fk2p8l%2FbtsFD5tyOSV%2FoHwHkcSiGoZaCIeXdkubdk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;594&quot; height=&quot;249&quot; data-origin-width=&quot;594&quot; data-origin-height=&quot;249&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;9. 실행&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이제 Run and Debug 를 다시 클릭하면 아래처럼 Ubuntu 의 컴파일러가 뜬다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;난 c++ 이니 두번째 g++ 을 선택했다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;853&quot; data-origin-height=&quot;222&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cahTRn/btsFB5VG02J/YCPE8KW0ScKvyrX6WeJLXK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cahTRn/btsFB5VG02J/YCPE8KW0ScKvyrX6WeJLXK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cahTRn/btsFB5VG02J/YCPE8KW0ScKvyrX6WeJLXK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcahTRn%2FbtsFB5VG02J%2FYCPE8KW0ScKvyrX6WeJLXK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;853&quot; height=&quot;222&quot; data-origin-width=&quot;853&quot; data-origin-height=&quot;222&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 VS Code 에서 아래 TERMINAL 을 선택하면 해당 코드가 실행되어 결과를 출력한 것을 확인할 수 있다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;460&quot; data-origin-height=&quot;166&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/buXMdR/btsFChO5oz9/LcsHmMr9Vwvu1KCtp3bWEK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/buXMdR/btsFChO5oz9/LcsHmMr9Vwvu1KCtp3bWEK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/buXMdR/btsFChO5oz9/LcsHmMr9Vwvu1KCtp3bWEK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbuXMdR%2FbtsFChO5oz9%2FLcsHmMr9Vwvu1KCtp3bWEK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;460&quot; height=&quot;166&quot; data-origin-width=&quot;460&quot; data-origin-height=&quot;166&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;10. Break Point&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 이 글을 쓰는 목적, Break point 테스트.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Visual Studio 의 단축키 (F9) 와 같게 Break Point 걸고 실행하면,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래처럼 브레이크 걸려 각 변수값을 확인할 수 있으며,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;F10, F11 로 진행할 수 있다. 우왕~&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;572&quot; data-origin-height=&quot;447&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/wmhB8/btsFCvNjjdK/XXM5hyRcdNkF2AX7rgSDz1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/wmhB8/btsFCvNjjdK/XXM5hyRcdNkF2AX7rgSDz1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/wmhB8/btsFCvNjjdK/XXM5hyRcdNkF2AX7rgSDz1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FwmhB8%2FbtsFCvNjjdK%2FXXM5hyRcdNkF2AX7rgSDz1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;572&quot; height=&quot;447&quot; data-origin-width=&quot;572&quot; data-origin-height=&quot;447&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/Linux</category>
      <category>visual studio code remote ssh</category>
      <category>vs code remote debugging</category>
      <category>vscode ssh</category>
      <category>vscode 원격 디버깅</category>
      <category>vscode 원격 컴파일</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/325</guid>
      <comments>https://hahaite.tistory.com/325#entry325comment</comments>
      <pubDate>Fri, 8 Mar 2024 14:50:35 +0900</pubDate>
    </item>
    <item>
      <title>2차원 벡터를 포인터로 넘겨 사용하기</title>
      <link>https://hahaite.tistory.com/324</link>
      <description>&lt;p data-ke-size=&quot;size16&quot;&gt;도움받은 사이트 :&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://leeeegun.tistory.com/3&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://leeeegun.tistory.com/3&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://stackoverflow.com/questions/6946217/how-to-access-the-contents-of-a-vector-from-a-pointer-to-the-vector-in-c&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://stackoverflow.com/questions/6946217/how-to-access-the-contents-of-a-vector-from-a-pointer-to-the-vector-in-c&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;첫번째 링크 글에서 2차원 벡터 사용법을 쉽게 익힐 수 있었다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그렇게 생성한 2차원 벡터를 포인터로 넘길 일이 있었는데 뜻대로 안되어 살펴보니&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;포인터로 넘겨진 2차원 벡터는 행렬기호 (대괄호) 를 사용할 수 없고 at() 함수를 통해 접근해야 했다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(위 스택오버플로우 링크 참조)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;만약 대괄호를 계속 사용하고 싶으면&amp;nbsp; 레퍼런스(Reference)로 넘겨 사용해야 한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;깔끔하게 레퍼런스로 넘기면 되겠지만,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;선언과 동시에 할당해야 하는 레퍼런스 특성상 사용하기 까칠한 상황이 발생했다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;어쨌든, 아래처럼 두가지의 경우를 정리해 본다.&lt;/p&gt;
&lt;pre id=&quot;code_1707812346230&quot; class=&quot;cpp&quot; data-ke-language=&quot;cpp&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;#include &amp;lt;cstdio&amp;gt;
#include &amp;lt;vector&amp;gt;

using namespace std ;

int callByPointer(vector&amp;lt;vector&amp;lt;int&amp;gt; &amp;gt;* pVecData)
{
	printf(&quot;============== Call by Pointer\n&quot;) ;
	printf(&quot;Size : [%ld][%ld]\n&quot;, pVecData-&amp;gt;size(), pVecData-&amp;gt;at(0).size()) ;

	for(int ii = 0; ii &amp;lt; pVecData-&amp;gt;size(); ii++)
	{
		for(int jj = 0; jj &amp;lt; pVecData-&amp;gt;at(0).size(); jj++)
			printf(&quot;%d &quot;, pVecData-&amp;gt;at(ii).at(jj)) ;
		printf(&quot;\n&quot;) ;
	}
	return 1 ;
}

int callByReference(vector&amp;lt;vector&amp;lt;int&amp;gt; &amp;gt;&amp;amp; pVecData)
{
	printf(&quot;============== Call by Reference\n&quot;) ;
	printf(&quot;Size : [%ld][%ld]\n&quot;, pVecData.size(), pVecData[0].size()) ;

	for(int ii = 0; ii &amp;lt; pVecData.size(); ii++)
	{
		for(int jj = 0; jj &amp;lt; pVecData[0].size(); jj++)
			printf(&quot;%d &quot;, pVecData[ii][jj]) ;
		printf(&quot;\n&quot;) ;
	}
	return 1 ;
}

int main()
{
	vector&amp;lt;vector&amp;lt;int&amp;gt; &amp;gt; vecData ;
	vector&amp;lt;int&amp;gt; vecField ;

	vecData.clear() ;
	vecField.clear() ;

	vecField.push_back(2) ;
	vecField.push_back(3) ;
	vecField.push_back(4) ;
	vecData.push_back(vecField) ;

	vecField.clear() ;
	vecField.push_back(5) ;
	vecField.push_back(6) ;
	vecField.push_back(7) ;
	vecData.push_back(vecField) ;

	printf(&quot;==============\n&quot;) ;
	printf(&quot;size : [%ld][%ld]\n&quot;, vecData.size(), vecData[0].size()) ;
	for(int ii = 0; ii &amp;lt; vecData.size(); ii++)
	{
		for(int jj = 0; jj &amp;lt; vecData[0].size(); jj++)
			printf(&quot;%d &quot;, vecData[ii][jj]) ;
		printf(&quot;\n&quot;) ;
	}

	// by Pointer
	callByPointer(&amp;amp;vecData) ;

	// by Reference
	callByReference(vecData) ;
	return 1 ;
}&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;main() 함수의 출력값, callByPointer(), callByReference() 함수에서&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;동일하게 값을 출력함을 확인하였다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;362&quot; data-origin-height=&quot;227&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cwthdU/btsEPKcnzWi/9XK4DLWxqqSb75gJ75T8JK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cwthdU/btsEPKcnzWi/9XK4DLWxqqSb75gJ75T8JK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cwthdU/btsEPKcnzWi/9XK4DLWxqqSb75gJ75T8JK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcwthdU%2FbtsEPKcnzWi%2F9XK4DLWxqqSb75gJ75T8JK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;362&quot; height=&quot;227&quot; data-origin-width=&quot;362&quot; data-origin-height=&quot;227&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/C,C++</category>
      <category>2차원 벡터</category>
      <category>2차원 벡터 포인터</category>
      <category>벡터 포인터</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/324</guid>
      <comments>https://hahaite.tistory.com/324#entry324comment</comments>
      <pubDate>Tue, 13 Feb 2024 17:33:07 +0900</pubDate>
    </item>
    <item>
      <title>Docker Redmine 설치 및 외부 MariaDB와의 연동</title>
      <link>https://hahaite.tistory.com/323</link>
      <description>&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #781b33;&quot;&gt;&amp;clubs; 도움받은 사이트&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;docker-redmine : &lt;a href=&quot;https://hub.docker.com/_/redmine&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://hub.docker.com/_/redmine&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;밍구의 코딩레시피 : &lt;a href=&quot;https://minggu92.tistory.com/81&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://minggu92.tistory.com/81&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;MeetUp (NHN) : &lt;a href=&quot;https://meetup.nhncloud.com/posts/277&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://meetup.nhncloud.com/posts/277&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Docker 공식사이트 :&amp;nbsp;&lt;a href=&quot;https://docs.docker.com/compose/compose-file/compose-versioning/&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://docs.docker.com/compose/compose-file/compose-versioning/&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Nirsa :&amp;nbsp;&lt;a href=&quot;https://nirsa.tistory.com/170&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://nirsa.tistory.com/170&lt;/a&gt; ( Docker 부팅 시 자동실행)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #781b33;&quot;&gt; &amp;clubs; 환경&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- Ubuntu Server 22&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- MariaDB Server 10.6&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #781b33;&quot;&gt;&amp;clubs; 목적&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;Ubuntu Server 에는 이미 MariaDB 가 설치되어 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;Redmine 은 Docker 를 사용해 설치하고, DB 연동은 이미 설치된 MariaDB를 사용한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;Redmine 은 docker-compose 를 사용하여 실행한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;MariaDB 설치 및 docker 관련 세부 명령어는 이 글에서 다루지 않는다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #781b33;&quot;&gt;&amp;clubs; docker 및 docker redmine 설치&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;docker, docker-compose 을 설치한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ sudo apt install docker&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt; $ sudo apt install docker-compose&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt; $ sudo apt install docker-compose-v2&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #781b33;&quot;&gt;&amp;clubs; MariaDB 에 Redmine 계정 생성&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;Redmine 자료가 저장될 MariaDB 에 Redmine 에서 사용할 계정을 만든다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ mysql -u root -p&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;로그인 되면,&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;1. 사용할 database 를 생성함. (아래 &quot;redmine&quot; 은 예제임. 수정 가능)&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;2. redmine DB 계정 및 패스워드 생성 (아래 &quot;redmine&quot; 계정 및 PW는 예제임. 수정가능)&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;3. 계정에 권한 부여&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;4. flush~&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt; MariaDB&amp;gt;&amp;nbsp; create&amp;nbsp;database&amp;nbsp;redmine&amp;nbsp;; &lt;/span&gt;&lt;br /&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt; MariaDB&amp;gt;&amp;nbsp; create&amp;nbsp;user&amp;nbsp;redmine@'%'&amp;nbsp;identified&amp;nbsp;by&amp;nbsp;'qwerty123@'&amp;nbsp;; &lt;/span&gt;&lt;br /&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt; MariaDB&amp;gt;&amp;nbsp; grant&amp;nbsp;all&amp;nbsp;privileges&amp;nbsp;on&amp;nbsp;redmine.*&amp;nbsp;to&amp;nbsp;'redmine'@'%'&amp;nbsp;; &lt;/span&gt;&lt;br /&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt; MariaDB&amp;gt;&amp;nbsp; flush&amp;nbsp;privileges&amp;nbsp;;&lt;/span&gt; &lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #781b33;&quot;&gt;&amp;clubs; docker-compose 작성&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;compose 가 저장될 디렉토리를 하나 만들어준다. 아래는 예시이다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ mkdir docker-redmine&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ cd docker-redmine&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;compose 파일을 작성한다. 파일 생성 후,&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ vi compose.yaml&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;그리고 아래처럼 작성해 준다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;아래 version 은 Compose File 버전이다. 이 값은 설치된 docker 버전을 따른다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ docker --version&lt;/span&gt;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;426&quot; data-origin-height=&quot;59&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cCaCSY/btsDULCYSgA/kicUte6AzpU6zTApotVNI1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cCaCSY/btsDULCYSgA/kicUte6AzpU6zTApotVNI1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cCaCSY/btsDULCYSgA/kicUte6AzpU6zTApotVNI1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcCaCSY%2FbtsDULCYSgA%2FkicUte6AzpU6zTApotVNI1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;426&quot; height=&quot;59&quot; data-origin-width=&quot;426&quot; data-origin-height=&quot;59&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;설치된 docker version 은 24.0.5 이다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이에 따른 compose 포맷 버전은 docker 공식 홈페이지에서 확인 가능하다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://docs.docker.com/compose/compose-file/compose-versioning/&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://docs.docker.com/compose/compose-file/compose-versioning/&lt;/a&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;789&quot; data-origin-height=&quot;205&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bdLItM/btsDQ1mvhTZ/1vbNr3dEKTNDrArfyg8eJ1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bdLItM/btsDQ1mvhTZ/1vbNr3dEKTNDrArfyg8eJ1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bdLItM/btsDQ1mvhTZ/1vbNr3dEKTNDrArfyg8eJ1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbdLItM%2FbtsDQ1mvhTZ%2F1vbNr3dEKTNDrArfyg8eJ1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;789&quot; height=&quot;205&quot; data-origin-width=&quot;789&quot; data-origin-height=&quot;205&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위 글에 따르면 19.03 이상 버전은 3.8 을 따른다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;우리는 24.0 이니 3.8 이라고 썼다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;REDMINE_DB_MYSQL : DB 가 설치된 서버의 IP 나 hostname 을 적어준다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;Redmine 접속 시, http://192.168.0.143:8080 으로 접속한다면, 192.168.0.143 이 적혀야 한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;나머지 항목은 직관적이므로 따로 설명하지 않으며&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;본인 환경에 맞게 적절히 수정하여 사용한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;850&quot; data-origin-height=&quot;492&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/rjwDR/btsDRHuyMtp/JVGe2fuaRuS7GDWB1Upd6k/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/rjwDR/btsDRHuyMtp/JVGe2fuaRuS7GDWB1Upd6k/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/rjwDR/btsDRHuyMtp/JVGe2fuaRuS7GDWB1Upd6k/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FrjwDR%2FbtsDRHuyMtp%2FJVGe2fuaRuS7GDWB1Upd6k%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;850&quot; height=&quot;492&quot; data-origin-width=&quot;850&quot; data-origin-height=&quot;492&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;(아래는 복사용 )&lt;/p&gt;
&lt;table style=&quot;border-collapse: collapse; width: 100%;&quot; border=&quot;1&quot; data-ke-align=&quot;alignLeft&quot;&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td style=&quot;width: 100%;&quot;&gt;version:&amp;nbsp;'3.8'&amp;nbsp;&amp;nbsp;#&amp;nbsp;도커&amp;nbsp;버전에&amp;nbsp;맞는&amp;nbsp;버전으로&amp;nbsp;작성 &lt;br /&gt;&lt;br /&gt;services: &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;redmine: &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;image:&amp;nbsp;'redmine' &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;restart:&amp;nbsp;always &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;ports: &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;-&amp;nbsp;'80:3000' &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;-&amp;nbsp;'8080:3000' &lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;environment: &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;TZ:&amp;nbsp;Asia/Seoul &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;REDMINE_DB_MYSQL:&amp;nbsp;192.168.0.143 &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;REDMINE_DB_PORT:&amp;nbsp;3306 &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;REDMINE_DB_DATABASE:&amp;nbsp;redmine &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;REDMINE_DB_USERNAME:&amp;nbsp;redmine &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;REDMINE_DB_PASSWORD:&amp;nbsp;qwerty123@ &lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;volumes: &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;-&amp;nbsp;'/home/hahaite/docker-redmine/data/files:/usr/src/redmine/files' &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;-&amp;nbsp;'/home/hahaite/docker-redmine/data/configuration.yml:/usr/src/redmine/config/configuration.yml' &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;-&amp;nbsp;'/home/hahaite/docker-redmine/data/themes:/usr/src/redmine/public/themes' &lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;-&amp;nbsp;'/home/hahaite/docker-redmine/data/plugins:/usr/src/redmine/plugins' &lt;br /&gt;&lt;br /&gt;#&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;-&amp;nbsp;'/mesData/docker-redmine/data:/home/redmine/data' &lt;br /&gt;#&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;-&amp;nbsp;'/etc/localtime:/etc/localtime' &lt;br /&gt;&lt;br /&gt;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;&amp;nbsp;container_name:&amp;nbsp;'redmine' &lt;br /&gt;&lt;br /&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #781b33;&quot;&gt;&amp;clubs; docker-compose 실행&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;compose.yaml 파일이 있는 디렉토리에서,&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ sudo docker-compose up&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이라고 명령을 치면 docker-redmine 이 실행된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;주로 나오는 에러는 DB 에 접속할 수 없다는 내용인데, IP 및 DB 계정을 확인해 본다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이상이 없으면 MariaDB 의 config 파일을 확인해 본다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ cd /etc/mysql/mariadb.conf.d&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ vi 50-server.cnf&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위 파일을 열어서 bind-address 가 127.0.0.1 인지 확인한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;만약 위 값이 세팅되어 있으면 주석처리한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;542&quot; data-origin-height=&quot;135&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/K4mht/btsDRIG2fpV/NKSl8oSXNJy9AmZiwCG9Ik/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/K4mht/btsDRIG2fpV/NKSl8oSXNJy9AmZiwCG9Ik/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/K4mht/btsDRIG2fpV/NKSl8oSXNJy9AmZiwCG9Ik/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FK4mht%2FbtsDRIG2fpV%2FNKSl8oSXNJy9AmZiwCG9Ik%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;542&quot; height=&quot;135&quot; data-origin-width=&quot;542&quot; data-origin-height=&quot;135&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;그리고 mariadb 를 재실행하고,&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ service mariadb restart&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;docker-redmine 을 재실행한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;별 에러없이 실행이 되면 아래처럼 접속되는지 확인한다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;397&quot; data-origin-height=&quot;274&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/U4R56/btsDVonfGwP/jMGyK5nR5qk9j7EhpAo15K/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/U4R56/btsDVonfGwP/jMGyK5nR5qk9j7EhpAo15K/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/U4R56/btsDVonfGwP/jMGyK5nR5qk9j7EhpAo15K/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FU4R56%2FbtsDVonfGwP%2FjMGyK5nR5qk9j7EhpAo15K%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;397&quot; height=&quot;274&quot; data-origin-width=&quot;397&quot; data-origin-height=&quot;274&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;본 절에선 심플하게 Redmine 을 설치하는 법을 다루었으며,&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;다음엔 보안을 적용해 https 접속을 다룰 예정이다.&lt;/p&gt;</description>
      <category>삽질미학/Linux</category>
      <category>docker</category>
      <category>docker redmine</category>
      <category>docker-compose</category>
      <category>Redmine</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/323</guid>
      <comments>https://hahaite.tistory.com/323#entry323comment</comments>
      <pubDate>Wed, 24 Jan 2024 12:13:07 +0900</pubDate>
    </item>
    <item>
      <title>VirtualBox IP 설정 - NAT, 호스트 전용 어댑터 조합</title>
      <link>https://hahaite.tistory.com/322</link>
      <description>&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 도움받은 사이트&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- Development notes (&lt;a href=&quot;https://whitekeyboard.tistory.com/730&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://whitekeyboard.tistory.com/730&lt;/a&gt; )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- 피어몬트, 그곳에 가면... (&lt;a href=&quot;https://blog.startsomething.dev/2018/10/26/virtualbox-%EC%97%90%EC%84%9C-nat-%EC%99%80-host-only-network-%EC%84%A4%EC%A0%95%ED%95%98%EA%B8%B0/&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://blog.startsomething.dev/2018/10/26/virtualbox-%EC%97%90%EC%84%9C-nat-%EC%99%80-host-only-network-%EC%84%A4%EC%A0%95%ED%95%98%EA%B8%B0/&lt;/a&gt; )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- WP Diaries ( &lt;a href=&quot;https://www.wpdiaries.com/virtualbox-for-web-development/&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://www.wpdiaries.com/virtualbox-for-web-development/&lt;/a&gt; )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- 타쿠대디 ( &lt;a href=&quot;https://takudaddy.tistory.com/352&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://takudaddy.tistory.com/352&lt;/a&gt; )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;- 코덕 개발자노트 ( &lt;a href=&quot;https://cjwoov.tistory.com/11&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://cjwoov.tistory.com/11&lt;/a&gt; )&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;예전에 VirtualBox 의 브릿지와 NAT 개념 관련 글을 쓴 적이 있는데&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그 때만 하더라도 자료가 많치 않았다. 2015년이니 9년 전이네... ㅋ~&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Link : &lt;a href=&quot;https://hahaite.tistory.com/283&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://hahaite.tistory.com/283&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;최근에 관련하여 찾아보니 윗글보다 훨씬 자세하고 쉽게 쓴 글이 수두룩하다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;Link : &lt;a href=&quot;https://takudaddy.tistory.com/352&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://takudaddy.tistory.com/352&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1705975882530&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;article&quot; data-og-title=&quot;Virtual Box 네트워크 설정 정리&quot; data-og-description=&quot;[목차] 1. 들어가며 2. 기본 용어 정리 3. 네트워크 방식 설명 4. 참고 [들어가며] 버추얼박스로 취약 서버를 구축해 테스트 및 실습을 해야 할 일이 많은데 가상 서버간의 네트워크 통신과 관련한 &quot; data-og-host=&quot;takudaddy.tistory.com&quot; data-og-source-url=&quot;https://takudaddy.tistory.com/352&quot; data-og-url=&quot;https://takudaddy.tistory.com/352&quot; data-og-image=&quot;https://scrap.kakaocdn.net/dn/drpFPi/hyU8SexUWA/99O3Mvm4cScqmTKTY8VJR0/img.png?width=800&amp;amp;height=470&amp;amp;face=0_0_800_470,https://scrap.kakaocdn.net/dn/X70sd/hyU8VPTvpD/AVIV1hWXwRJNuSVwKbg0L0/img.png?width=800&amp;amp;height=470&amp;amp;face=0_0_800_470,https://scrap.kakaocdn.net/dn/qwfOS/hyU85LJyR4/97Rxubjl50X1cakyn2vt11/img.png?width=936&amp;amp;height=551&amp;amp;face=0_0_936_551&quot;&gt;&lt;a href=&quot;https://takudaddy.tistory.com/352&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://takudaddy.tistory.com/352&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url('https://scrap.kakaocdn.net/dn/drpFPi/hyU8SexUWA/99O3Mvm4cScqmTKTY8VJR0/img.png?width=800&amp;amp;height=470&amp;amp;face=0_0_800_470,https://scrap.kakaocdn.net/dn/X70sd/hyU8VPTvpD/AVIV1hWXwRJNuSVwKbg0L0/img.png?width=800&amp;amp;height=470&amp;amp;face=0_0_800_470,https://scrap.kakaocdn.net/dn/qwfOS/hyU85LJyR4/97Rxubjl50X1cakyn2vt11/img.png?width=936&amp;amp;height=551&amp;amp;face=0_0_936_551');&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;Virtual Box 네트워크 설정 정리&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;[목차] 1. 들어가며 2. 기본 용어 정리 3. 네트워크 방식 설명 4. 참고 [들어가며] 버추얼박스로 취약 서버를 구축해 테스트 및 실습을 해야 할 일이 많은데 가상 서버간의 네트워크 통신과 관련한&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;takudaddy.tistory.com&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Link : &lt;a href=&quot;https://cjwoov.tistory.com/11&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://cjwoov.tistory.com/11&lt;/a&gt;&lt;/p&gt;
&lt;figure id=&quot;og_1705975911108&quot; contenteditable=&quot;false&quot; data-ke-type=&quot;opengraph&quot; data-ke-align=&quot;alignCenter&quot; data-og-type=&quot;article&quot; data-og-title=&quot;[VM] VirtualBox  네트워크 설정 상세 분석&quot; data-og-description=&quot;본 포스트는 https://technology.amis.nl/2018/07/27/virtualbox-networking-explained를 번역 &amp;amp; 가공하였습니다. 1. 서론 2. 네트워크 옵션 2.1 내부 네트워크 2.2 NAT 2.3 NAT 네트워크 2.4 호스트 전용 어댑터 2.5 브릿지 네&quot; data-og-host=&quot;cjwoov.tistory.com&quot; data-og-source-url=&quot;https://cjwoov.tistory.com/11&quot; data-og-url=&quot;https://cjwoov.tistory.com/11&quot; data-og-image=&quot;https://scrap.kakaocdn.net/dn/Ro4kW/hyU8QnvXXa/FtHiDo1g41pFXgeWZNu1Y0/img.png?width=573&amp;amp;height=450&amp;amp;face=0_0_573_450,https://scrap.kakaocdn.net/dn/bOEhBs/hyU8VWFHYt/FZZWDDPRiCFKNKBR3K96Nk/img.png?width=573&amp;amp;height=450&amp;amp;face=0_0_573_450,https://scrap.kakaocdn.net/dn/sXfwE/hyU82IeXxQ/KhDjcVTfjMKHSSFMWsLW7k/img.png?width=1161&amp;amp;height=441&amp;amp;face=0_0_1161_441&quot;&gt;&lt;a href=&quot;https://cjwoov.tistory.com/11&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot; data-source-url=&quot;https://cjwoov.tistory.com/11&quot;&gt;
&lt;div class=&quot;og-image&quot; style=&quot;background-image: url('https://scrap.kakaocdn.net/dn/Ro4kW/hyU8QnvXXa/FtHiDo1g41pFXgeWZNu1Y0/img.png?width=573&amp;amp;height=450&amp;amp;face=0_0_573_450,https://scrap.kakaocdn.net/dn/bOEhBs/hyU8VWFHYt/FZZWDDPRiCFKNKBR3K96Nk/img.png?width=573&amp;amp;height=450&amp;amp;face=0_0_573_450,https://scrap.kakaocdn.net/dn/sXfwE/hyU82IeXxQ/KhDjcVTfjMKHSSFMWsLW7k/img.png?width=1161&amp;amp;height=441&amp;amp;face=0_0_1161_441');&quot;&gt;&amp;nbsp;&lt;/div&gt;
&lt;div class=&quot;og-text&quot;&gt;
&lt;p class=&quot;og-title&quot; data-ke-size=&quot;size16&quot;&gt;[VM] VirtualBox 네트워크 설정 상세 분석&lt;/p&gt;
&lt;p class=&quot;og-desc&quot; data-ke-size=&quot;size16&quot;&gt;본 포스트는 https://technology.amis.nl/2018/07/27/virtualbox-networking-explained를 번역 &amp;amp; 가공하였습니다. 1. 서론 2. 네트워크 옵션 2.1 내부 네트워크 2.2 NAT 2.3 NAT 네트워크 2.4 호스트 전용 어댑터 2.5 브릿지 네&lt;/p&gt;
&lt;p class=&quot;og-host&quot; data-ke-size=&quot;size16&quot;&gt;cjwoov.tistory.com&lt;/p&gt;
&lt;/div&gt;
&lt;/a&gt;&lt;/figure&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;관련 개념은 위 두 링크를 참고바라며 아래는 위 개념을 어느정도 알고 있다고 가정하고 쓴다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;* 호스트 : Windows 11&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;* 게스트 : Ubuntu server 22&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(한마디로 윈도우에 VirtualBox 설치했고, VirtualBox 사용해서 리눅스 돌리고 있다.)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&amp;clubs; 어댑터에 브릿지&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;리눅스는 IPTime&amp;nbsp; 과 같은 외부 공유기로부터 IP를 받는다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;제일 깔끔한 방법이나 공유기가 필요하다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(그래서 출장갈 때 항상 공유기를 챙겼던 시절이 있었다. ㅋ)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&amp;clubs; NAT&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;NAT 로 설정하면 리눅스는 10.0.2.15 의 IP를 할당받는다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 리눅스에 접속할 때 아래 192.168.56.1 로 리눅스에 접속할 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;819&quot; data-origin-height=&quot;345&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/clLF08/btsDLuCmD4K/7WVshBzVaBGmOz5JkuyUgK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/clLF08/btsDLuCmD4K/7WVshBzVaBGmOz5JkuyUgK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/clLF08/btsDLuCmD4K/7WVshBzVaBGmOz5JkuyUgK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FclLF08%2FbtsDLuCmD4K%2F7WVshBzVaBGmOz5JkuyUgK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;819&quot; height=&quot;345&quot; data-origin-width=&quot;819&quot; data-origin-height=&quot;345&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그러나 포트포워딩 귀차니즘이 있고 게스트 간에 통신이 안되는 이슈가 있다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;637&quot; data-origin-height=&quot;110&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bFpsuq/btsDTu8NSir/QmHzCOtuayt8taXcePUn41/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bFpsuq/btsDTu8NSir/QmHzCOtuayt8taXcePUn41/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bFpsuq/btsDTu8NSir/QmHzCOtuayt8taXcePUn41/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbFpsuq%2FbtsDTu8NSir%2FQmHzCOtuayt8taXcePUn41%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;637&quot; height=&quot;110&quot; data-origin-width=&quot;637&quot; data-origin-height=&quot;110&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&amp;clubs; 호스트 전용 어댑터&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;호스트 전용 어댑터로 설정하면 아래처럼 192.168.56.xxx 로 IP 가 할당된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(이 IP는 192.168.56.1 가상 공유기로부터 DHCP 로 할당받는 것으로 알고 있다.)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 호스트에서 이 IP 로 접속하면 된다. (NAT와 달리 포트포워딩 필요없음)&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;301&quot; data-origin-height=&quot;103&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cskaxi/btsDNsYzOey/h5BKuZdwxXEo0qQplrhSpk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cskaxi/btsDNsYzOey/h5BKuZdwxXEo0qQplrhSpk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cskaxi/btsDNsYzOey/h5BKuZdwxXEo0qQplrhSpk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fcskaxi%2FbtsDNsYzOey%2Fh5BKuZdwxXEo0qQplrhSpk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;301&quot; height=&quot;103&quot; data-origin-width=&quot;301&quot; data-origin-height=&quot;103&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;하지만 결정적으로 외부 접속 (인터넷 등)이 안된다. OTL&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;459&quot; data-origin-height=&quot;92&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/1fLn3/btsDQdmAvHC/kT8HyzzvBtuKSqIlriEO50/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/1fLn3/btsDQdmAvHC/kT8HyzzvBtuKSqIlriEO50/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/1fLn3/btsDQdmAvHC/kT8HyzzvBtuKSqIlriEO50/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F1fLn3%2FbtsDQdmAvHC%2FkT8HyzzvBtuKSqIlriEO50%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;459&quot; height=&quot;92&quot; data-origin-width=&quot;459&quot; data-origin-height=&quot;92&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&amp;clubs; NAT + 호스트 전용 어댑터 조합&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;표 출처 : 코덕 개발자 노트 ( &lt;a href=&quot;https://cjwoov.tistory.com/11&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://cjwoov.tistory.com/11&lt;/a&gt; )&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;783&quot; data-origin-height=&quot;218&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/KSQMZ/btsDJDNBZof/8Ckkd59CySyUtBuNLTCcPK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/KSQMZ/btsDJDNBZof/8Ckkd59CySyUtBuNLTCcPK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/KSQMZ/btsDJDNBZof/8Ckkd59CySyUtBuNLTCcPK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FKSQMZ%2FbtsDJDNBZof%2F8Ckkd59CySyUtBuNLTCcPK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;783&quot; height=&quot;218&quot; data-origin-width=&quot;783&quot; data-origin-height=&quot;218&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;VirtualBox 는 복수의 네트워크 어댑터 설정이 가능하다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;즉, 어댑터 1에는 NAT 로, 어댑터 2 에는 호스트 전용 어댑터로 설정하여 상호 단점을 보완하는 것이다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;777&quot; data-origin-height=&quot;224&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/Li8N9/btsDQV6Zbkp/34B2lWJ4XMZ7hgDxB2rUk1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/Li8N9/btsDQV6Zbkp/34B2lWJ4XMZ7hgDxB2rUk1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/Li8N9/btsDQV6Zbkp/34B2lWJ4XMZ7hgDxB2rUk1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FLi8N9%2FbtsDQV6Zbkp%2F34B2lWJ4XMZ7hgDxB2rUk1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;777&quot; height=&quot;224&quot; data-origin-width=&quot;777&quot; data-origin-height=&quot;224&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 후, 게스트 접속은 호스트 전용 어댑터 IP 로 (192.168.56.xxx ) 접속할 수 있으며&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;게스트의 외부망 접속은 NAT 를 통해 이루어지게 된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;여기까지 하고 ifconfig 해보면 NAT 설정 IP (10.0.2.15) 만 나타나고&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;호스트 전용 어댑터 (192.168.56.xxx ) 는 안보인다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;437&quot; data-origin-height=&quot;284&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/lRzw2/btsDLJl1eJm/9BhZFvOYz34iisc2xk7PCk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/lRzw2/btsDLJl1eJm/9BhZFvOYz34iisc2xk7PCk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/lRzw2/btsDLJl1eJm/9BhZFvOYz34iisc2xk7PCk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FlRzw2%2FbtsDLJl1eJm%2F9BhZFvOYz34iisc2xk7PCk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;437&quot; height=&quot;284&quot; data-origin-width=&quot;437&quot; data-origin-height=&quot;284&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그런데 ip addr 명령어로 보면 아래처럼 IP 할당이 안된 이더넷이 하나 보인다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 놈이 호스트 전용 어댑터의 이더넷임을 알 수 있다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;513&quot; data-origin-height=&quot;356&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/eADzQS/btsDRLDaVtY/GUBRHMNziyEkCr7o61KOvk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/eADzQS/btsDRLDaVtY/GUBRHMNziyEkCr7o61KOvk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/eADzQS/btsDRLDaVtY/GUBRHMNziyEkCr7o61KOvk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FeADzQS%2FbtsDRLDaVtY%2FGUBRHMNziyEkCr7o61KOvk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;513&quot; height=&quot;356&quot; data-origin-width=&quot;513&quot; data-origin-height=&quot;356&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이에 (위의 경우) enp0s8 에 IP 를 할당해 준다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;본 글의 예제는 Ubuntu Server 22 환경이므로, 이 환경에 맞게 아래처럼 작업해 준다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(당연한 얘기지만 각각의 게스트 OS 에 맞게 설정해 준다.)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래는 호스트 전용 어댑터에 192.168.56.5 에 Subnet Mask 255.255.255.0 을 적용한 예이다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ cd /etc/netplan&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;$ sudo vi 00-installer-config.yaml&lt;/span&gt;&amp;nbsp; (파일명은 다를 수 있음)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 아래처럼 호스트 전용 어댑터(enp0s8) 부분을 추가하였다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;427&quot; data-origin-height=&quot;165&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/b3qCPy/btsDSspW7G0/0zDgtRjLqgESiGk6a97B00/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/b3qCPy/btsDSspW7G0/0zDgtRjLqgESiGk6a97B00/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/b3qCPy/btsDSspW7G0/0zDgtRjLqgESiGk6a97B00/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fb3qCPy%2FbtsDSspW7G0%2F0zDgtRjLqgESiGk6a97B00%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;427&quot; height=&quot;165&quot; data-origin-width=&quot;427&quot; data-origin-height=&quot;165&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그리고 아래 명령어 적용하거나 재부팅하여 ifconfig 해보면,&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;$ sudo netplan apply&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;$ ifconfig&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;아래처럼 호스트 전용 어댑터를 확인할 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이제 게스트에서 아래 IP 192.168.56.5 로 접속하면 된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;또한 NAT 어댑터를 통해 외부접속도 가능한 환경이 된다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;422&quot; data-origin-height=&quot;303&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/dYOiLx/btsDQ8FpPLx/GdgueNjn0uh1HW7givOZl1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/dYOiLx/btsDQ8FpPLx/GdgueNjn0uh1HW7givOZl1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/dYOiLx/btsDQ8FpPLx/GdgueNjn0uh1HW7givOZl1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FdYOiLx%2FbtsDQ8FpPLx%2FGdgueNjn0uh1HW7givOZl1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;422&quot; height=&quot;303&quot; data-origin-width=&quot;422&quot; data-origin-height=&quot;303&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;b&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&amp;clubs; 덧글&lt;/span&gt;&lt;/b&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://blog.startsomething.dev/2018/10/26/virtualbox-%EC%97%90%EC%84%9C-nat-%EC%99%80-host-only-network-%EC%84%A4%EC%A0%95%ED%95%98%EA%B8%B0/&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://blog.startsomething.dev/2018/10/26/virtualbox-%EC%97%90%EC%84%9C-nat-%EC%99%80-host-only-network-%EC%84%A4%EC%A0%95%ED%95%98%EA%B8%B0/&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위 글에 의하면 VirtualBox 전역도구에서&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;DHCP 사용 안함 및 &quot;수동으로 어댑터 설정&quot; 으로 설정하라고 하고 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;그런데 위 설정 시, DHCP 는 그냥 사용함으로 두어도 됐다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;혹시나 안되면 아래 설정 부분을 수정해 보자.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;795&quot; data-origin-height=&quot;470&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/pmUuq/btsDQ4JM8UQ/6SUOQKX8SlzkTfAapgK0mK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/pmUuq/btsDQ4JM8UQ/6SUOQKX8SlzkTfAapgK0mK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/pmUuq/btsDQ4JM8UQ/6SUOQKX8SlzkTfAapgK0mK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FpmUuq%2FbtsDQ4JM8UQ%2F6SUOQKX8SlzkTfAapgK0mK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;795&quot; height=&quot;470&quot; data-origin-width=&quot;795&quot; data-origin-height=&quot;470&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/Linux</category>
      <category>NAT</category>
      <category>VirtualBox</category>
      <category>VirtualBox IP 설정</category>
      <category>Virtualbox 네트워크 설정</category>
      <category>호스트 전용 어댑터</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/322</guid>
      <comments>https://hahaite.tistory.com/322#entry322comment</comments>
      <pubDate>Tue, 23 Jan 2024 14:00:51 +0900</pubDate>
    </item>
    <item>
      <title>Ubuntu Server에 LUKS 적용하기</title>
      <link>https://hahaite.tistory.com/321</link>
      <description>&lt;pre id=&quot;code_1697522008706&quot; class=&quot;bash&quot; data-ke-language=&quot;bash&quot; data-ke-type=&quot;codeblock&quot;&gt;&lt;code&gt;lsblk&lt;/code&gt;&lt;/pre&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 도움받은 사이트&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://sacstory.tistory.com/entry/%ED%95%98%EB%93%9C-%EC%B6%94%EA%B0%80%EC%8B%9C&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://sacstory.tistory.com/entry/%ED%95%98%EB%93%9C-%EC%B6%94%EA%B0%80%EC%8B%9C&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://access.redhat.com/documentation/ko-kr/red_hat_enterprise_linux/8/html/security_hardening/encrypting-block-devices-using-luks_security-hardening&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://access.redhat.com/documentation/ko-kr/red_hat_enterprise_linux/8/html/security_hardening/encrypting-block-devices-using-luks_security-hardening&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://blog.tinned-software.net/automount-a-luks-encrypted-volume-on-system-start/&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://blog.tinned-software.net/automount-a-luks-encrypted-volume-on-system-start/&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://ko.linux-console.net/?p=10366&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://ko.linux-console.net/?p=10366&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://ko.linux-console.net/?p=439&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://ko.linux-console.net/?p=439&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&lt;a href=&quot;https://ko.linux-console.net/?p=9102&quot; target=&quot;_blank&quot; rel=&quot;noopener&amp;nbsp;noreferrer&quot;&gt;https://ko.linux-console.net/?p=9102&lt;/a&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;갑님께서 생산용 서버의 Disk or File System 에&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Encryption 을 적용해 달라고 요청을 했다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;처음 해보는 작업이라 여분의 서버에 1TB 짜리 HDD 하나 꽂고&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;우분투만 6번을 설치하고 수십번의 재부팅 끝에 아래처럼 정리해 본다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt; &lt;b&gt;&amp;clubs; 목적&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;================================================&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Ubuntu Server (22.04) 의 Data 영역을&amp;nbsp; LUKS 로 암호화한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;윈도우에서 C에는 프로그램만, D에는 데이터를 저장하는데&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;D 드라이브만 암호화하는 것과 같다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;================================================&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;(Linux 초급 영역은 아닌지라 설명이 불친절할 수 있으며&amp;nbsp;나도 헷갈리는 부분의 용어, 개념 등이 틀릴 수 있다.)&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 파티션 전체에 LUKS 적용하기&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이미 설치된 Ubuntu 전체에 적용할 수도 있으나 절차가 복잡하였다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;Ubuntu 설치 시, 아래처럼 파티션에 LUKS 를 적용하는 옵션이 있었다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignCenter&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;906&quot; data-origin-height=&quot;379&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/9qz9E/btsyFpdQ43r/LmeBVuKk6H5DByx3Se1XS0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/9qz9E/btsyFpdQ43r/LmeBVuKk6H5DByx3Se1XS0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/9qz9E/btsyFpdQ43r/LmeBVuKk6H5DByx3Se1XS0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F9qz9E%2FbtsyFpdQ43r%2FLmeBVuKk6H5DByx3Se1XS0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;906&quot; height=&quot;379&quot; data-origin-width=&quot;906&quot; data-origin-height=&quot;379&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;위와 같이 심플하게 전체 영역에 LUKS 를 적용할 수 있다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 후, 하위에 생성되는 볼륨은 자동으로 LUKS 가 적용된다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 특정 볼륨에 LUKS 적용하기&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;Ubuntu 설치 시, LUKS 를 적용하지 않는 케이스이다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;단, LVM 은 적용한다. (위 이미지에서 Set up this disk as an LVM group )&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;저 항목을 선택하면 자동으로 아래처럼 파티션이 설정된다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;626&quot; data-origin-height=&quot;472&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/dDmlkr/btsyDAtFYJn/dADTevx35j6JTUEZZzksY0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/dDmlkr/btsyDAtFYJn/dADTevx35j6JTUEZZzksY0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/dDmlkr/btsyDAtFYJn/dADTevx35j6JTUEZZzksY0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FdDmlkr%2FbtsyDAtFYJn%2FdADTevx35j6JTUEZZzksY0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;626&quot; height=&quot;472&quot; data-origin-width=&quot;626&quot; data-origin-height=&quot;472&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;보면 1TB 중 100GB 만 할당된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;프로그램 등을 설치하면 이 100GB 영역에 설치될 것이다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;나는 Ubuntu 설치 후, 나머지 900GB 를 LUKS 로 암호화하고 Data 영역으로 사용할 예정이다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 볼륨 생성 후, LUKS 암호화 적용&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;Ubuntu 설치 후,&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;lsblk&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;하면 아래처럼 100GB 파티션만 표시된다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;574&quot; data-origin-height=&quot;197&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/u0Lgt/btsytPlzdKc/VLSx0W8AesbkyzvfLSrfhK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/u0Lgt/btsytPlzdKc/VLSx0W8AesbkyzvfLSrfhK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/u0Lgt/btsytPlzdKc/VLSx0W8AesbkyzvfLSrfhK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fu0Lgt%2FbtsytPlzdKc%2FVLSx0W8AesbkyzvfLSrfhK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;574&quot; height=&quot;197&quot; data-origin-width=&quot;574&quot; data-origin-height=&quot;197&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이에 나머지 영역에 추가로 볼륨을 생성해 준다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo lvcreate -l 100%FREE -n cryptdata-lv ubuntu-vg&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;아래처럼 ubuntu-vg 라는 Volume Group 에 cryptdata-lv 라는 Logical Volume 이 생성되었다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;592&quot; data-origin-height=&quot;211&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cW6r0T/btsywgCV3J3/gbt48LZkpKmLUJlFZ3pfT0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cW6r0T/btsywgCV3J3/gbt48LZkpKmLUJlFZ3pfT0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cW6r0T/btsywgCV3J3/gbt48LZkpKmLUJlFZ3pfT0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcW6r0T%2FbtsywgCV3J3%2Fgbt48LZkpKmLUJlFZ3pfT0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;592&quot; height=&quot;211&quot; data-origin-width=&quot;592&quot; data-origin-height=&quot;211&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이 볼륨을 LUKS 로 포멧시킨다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;LUKS 는 모두 cryptsetup 명령어로 수행된다. Ubuntu Server 22의 경우, 기본으로 설치되어 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;(luksFormat 에서 대문자 주의)&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo cryptsetup luksFormat /dev/ubuntu-vg/cryptdata-lv&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;정말 Format할지 물어보는데 대문자로 &quot;YES&quot; 를 입력한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이 후, 본 암호화볼륨을 사용하기 위한 패스워드를 설정해준다. (까먹으면 ㅈ된다.)&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 암호화 볼륨에 접근하기 위한 매핑네임 생성&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위 cryptdata-lv 볼륨은 LUKS로 암호화되어 있으므로 바로 사용할 수 없다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이에 매핑네임을 생성해 준다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;매핑네임은 내가 붙인 이름이다. 본명 볼륨은 아니고, man 을 봐도 그냥 name 으로 되어 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위에서 생성한 암호화된 볼륨 cryptdata-lv 에 mesdata 란 매핑네임을 생성해 주었다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo cryptsetup luksOpen /dev/ubuntu-vg/cryptdata-lv mesdata&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;암호화 볼륨에 접근하기 위한 패스워드를 물어보며 위에서 설정한 패스워드를 입력한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이렇게 생성하면 /dev/mapper/mesdata 가 생성된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이놈을 원하는 file format 에 맞게 포멧해 준다. 난 xfs 로 포멧하였다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo mkfs.xfs /dev/mapper/mesdata&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;lsblk 로 확인해 보면, 하위에 뭔가 생성된 것이 보인다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;612&quot; data-origin-height=&quot;261&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/yFvBm/btsyuLQDiZT/Qfc4QWg6LXRoHFgbEOSQ8k/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/yFvBm/btsyuLQDiZT/Qfc4QWg6LXRoHFgbEOSQ8k/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/yFvBm/btsyuLQDiZT/Qfc4QWg6LXRoHFgbEOSQ8k/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FyFvBm%2FbtsyuLQDiZT%2FQfc4QWg6LXRoHFgbEOSQ8k%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;612&quot; height=&quot;261&quot; data-origin-width=&quot;612&quot; data-origin-height=&quot;261&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;즉, LUKS 매핑네임 mesdata 는 암호화된 볼륨에 접근하기 위한 통로로 여기면 얼추 맞을 듯 하다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 암호화 영역 mount&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이제 위에서 생성한 암호화 영역을 사용하기 위해 특정 디렉토리로 마운트한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;나는 임의로 루트에 mesData 란 디렉토리를 생성했다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo mkdir /mesData&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;그리고 위 mesdata 매핑네임을 마운트한다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo mount /dev/mapper/mesdata /mesData&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이상없으면 아래처럼 매핑네임이 /mesData 디렉토리로 성공적으로 마운트됐음을 확인할 수 있다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;605&quot; data-origin-height=&quot;260&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/1rUCs/btsyuiVyphW/1BjYbBCe83k31RBH7nHSp0/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/1rUCs/btsyuiVyphW/1BjYbBCe83k31RBH7nHSp0/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/1rUCs/btsyuiVyphW/1BjYbBCe83k31RBH7nHSp0/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2F1rUCs%2FbtsyuiVyphW%2F1BjYbBCe83k31RBH7nHSp0%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;605&quot; height=&quot;260&quot; data-origin-width=&quot;605&quot; data-origin-height=&quot;260&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이제 마운트된 /mesData 에 데이터를 저장하면 데이터는 암호화되어 하드디스크에 저장된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;누군가 악의를 품고 하드디스크를 훔쳐서 읽으려 해도 암호화되어 있으므로 읽을 수 없다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이 상태에서 재부팅하면,&amp;nbsp;아래 상태로 돌아간다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;519&quot; data-origin-height=&quot;87&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/W3LeB/btsyufq2kbO/zA2k2GxYyttmzxsjoKy9B1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/W3LeB/btsyufq2kbO/zA2k2GxYyttmzxsjoKy9B1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/W3LeB/btsyufq2kbO/zA2k2GxYyttmzxsjoKy9B1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FW3LeB%2Fbtsyufq2kbO%2FzA2k2GxYyttmzxsjoKy9B1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;519&quot; height=&quot;87&quot; data-origin-width=&quot;519&quot; data-origin-height=&quot;87&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;그러면 다시 매핑 네임 생성해주고 -&amp;gt; 비밀번호 입력하고 -&amp;gt; 마운트 후, 사용하면 된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 부팅 시, 자동 매핑네임 생성 (패스워드 입력모드)&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;재부팅할 때마다 위와 같이 매번 매핑네임을 생성하는 것은 비효율적이다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;/etc/crypttab 파일을 수정하여 부팅 시, 매핑네임을 생성할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;1. 우선, 암호화된 볼륨의 UUID 를 얻는다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;cryptdata-lv 에 본인이 생성한 볼륨명을 적어준다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo cryptsetup luksUUID /dev/ubuntu-vg/cryptdata-lv&lt;/span&gt;&lt;/blockquote&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;594&quot; data-origin-height=&quot;49&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/cxPrIY/btsyDtO2sJ8/14r3kIdNxBqadkS02h2Dsk/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/cxPrIY/btsyDtO2sJ8/14r3kIdNxBqadkS02h2Dsk/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/cxPrIY/btsyDtO2sJ8/14r3kIdNxBqadkS02h2Dsk/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FcxPrIY%2FbtsyDtO2sJ8%2F14r3kIdNxBqadkS02h2Dsk%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;594&quot; height=&quot;49&quot; data-origin-width=&quot;594&quot; data-origin-height=&quot;49&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;2. /etc/crypttab 파일을 수정한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;아마도 위 절차를 거쳤으면 /etc/crypttab 파일이 있을 것이다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;여기에, 본인이 생성할 매핑네임, 위 1번에서 얻은 UUID, none, luks 를 적어준다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;아래는 예시이다. UUID= 부분에 주의한다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style3&quot;&gt;mesdata&amp;nbsp;UUID=6c2a7380-9214-4245-a946-29275f58e5d4&amp;nbsp;none&amp;nbsp;luks&lt;/blockquote&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;535&quot; data-origin-height=&quot;59&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/ctt3li/btsyEUZsxud/X9OzQzPRqEvBSkGMWZC811/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/ctt3li/btsyEUZsxud/X9OzQzPRqEvBSkGMWZC811/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/ctt3li/btsyEUZsxud/X9OzQzPRqEvBSkGMWZC811/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2Fctt3li%2FbtsyEUZsxud%2FX9OzQzPRqEvBSkGMWZC811%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;535&quot; height=&quot;59&quot; data-origin-width=&quot;535&quot; data-origin-height=&quot;59&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;3. 위와 같이 저장하고 재부팅하면 부팅할 때 암호화 볼륨의 패스워드를 물어본다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;입력 후, lsblk 하면 매핑네임이 생성된 것을 확인할 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;4. 이 후, 디렉토리에 마운트하여 사용한다. (자동 마운트는 저 아래에서~ )&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 부팅 시, 자동 매핑네임 생성 (키 파일 등록모드)&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;위와 같이 부팅 시, 패스워드를 입력하는 것이 좀 더 강력한 보안이 될 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;그러나 주어진 환경이 여의치 않을 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;필자는 서버가 베트남 공장에 설치되어 원격으로 작업을 진행한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;그런데 공장 사정으로 서버를 재부팅할 일이 생기면, 그 때마다 서버 관리자는&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;원격으로 접속하여 암호화 볼륨의 패스워드를 입력해야 한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;만약 입력할 수 없는 상황이면, 최악의 경우 생산 라인이 스톱된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;이에 패스워드 입력 없이 매핑네임을 생성하는 방법을 기술한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;1. 키 생성&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;특정 양식이 있는 것이 아니라 아무 파일이나 된다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;다른 사이트를 살펴봐도 랜덤하게 키를 생성하는 것을 볼 수 있다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;아래는 4k 짜리 랜덤한 파일을 생성하는 명령어이다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;dd if=/dev/urandom of=./keyfile bs=1024 count=4&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;2. 파일을 /etc 밑으로 옮긴다. (꼭 etc 아니어도 상관 없다.)&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo mv keyfile /etc&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;3. 해당 키를 암호화 블록에 등록한다. (패스워드 입력 필요)&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo cryptsetup luksAddKey /dev/ubuntu-vg/cryptdata-lv /etc/keyfile&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;아래처럼 키 등록이 됐는지 체크할 수 있다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style2&quot;&gt;&lt;span style=&quot;color: #006dd7;&quot;&gt;sudo cryptsetup luksDump /dev/ubuntu-vg/cryptdata-lv&lt;/span&gt;&lt;/blockquote&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;4. crypttab 파일에 키를 기재한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;/etc/crypttab 파일의 none 위치에 키 위치를 적어준다.&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;551&quot; data-origin-height=&quot;52&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/VGXBN/btsyHfvDja1/2sfXQC1neatavr5KGryOl1/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/VGXBN/btsyHfvDja1/2sfXQC1neatavr5KGryOl1/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/VGXBN/btsyHfvDja1/2sfXQC1neatavr5KGryOl1/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FVGXBN%2FbtsyHfvDja1%2F2sfXQC1neatavr5KGryOl1%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;551&quot; height=&quot;52&quot; data-origin-width=&quot;551&quot; data-origin-height=&quot;52&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;5. 재부팅 후, lsblk 로 매핑네임이 생성됐는지 확인한다.&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt;&amp;clubs; 디렉토리에 자동 마운트&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;서브 주제이기에 간단히 다룬다. /etc/fstab 을 열어 아래처럼 추가해주고 재부팅하면&lt;/p&gt;
&lt;p style=&quot;color: #333333; text-align: start;&quot; data-ke-size=&quot;size16&quot;&gt;매핑네임 mesdata 가 디렉토리 mesData 에 마운트된다.&lt;/p&gt;
&lt;blockquote data-ke-style=&quot;style3&quot;&gt;/dev/mapper/mesdata&amp;nbsp;/mesData&amp;nbsp;xfs&amp;nbsp;defaults&amp;nbsp;0&amp;nbsp;0&lt;/blockquote&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p&gt;&lt;figure class=&quot;imageblock alignLeft&quot; data-ke-mobileStyle=&quot;widthOrigin&quot; data-origin-width=&quot;644&quot; data-origin-height=&quot;241&quot;&gt;&lt;span data-url=&quot;https://blog.kakaocdn.net/dn/bDKo0P/btsyET7Pw3h/0gdKNqIW8oQT9EK16QHltK/img.png&quot; data-phocus=&quot;https://blog.kakaocdn.net/dn/bDKo0P/btsyET7Pw3h/0gdKNqIW8oQT9EK16QHltK/img.png&quot;&gt;&lt;img src=&quot;https://blog.kakaocdn.net/dn/bDKo0P/btsyET7Pw3h/0gdKNqIW8oQT9EK16QHltK/img.png&quot; srcset=&quot;https://img1.daumcdn.net/thumb/R1280x0/?scode=mtistory2&amp;fname=https%3A%2F%2Fblog.kakaocdn.net%2Fdn%2FbDKo0P%2FbtsyET7Pw3h%2F0gdKNqIW8oQT9EK16QHltK%2Fimg.png&quot; onerror=&quot;this.onerror=null; this.src='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png'; this.srcset='//t1.daumcdn.net/tistory_admin/static/images/no-image-v1.png';&quot; loading=&quot;lazy&quot; width=&quot;644&quot; height=&quot;241&quot; data-origin-width=&quot;644&quot; data-origin-height=&quot;241&quot;/&gt;&lt;/span&gt;&lt;/figure&gt;
&lt;/p&gt;
&lt;p data-ke-size=&quot;size18&quot;&gt;&lt;span style=&quot;color: #953b34;&quot;&gt;&lt;b&gt; &amp;clubs; 데이터 저장위치 변경&lt;/b&gt;&lt;/span&gt;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;이 후, 주요 데이터가 저장되는 위치를 /mesData 로 설정하여&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;데이터 저장 시 암호화를 적용한다.&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;
&lt;p data-ke-size=&quot;size16&quot;&gt;&amp;nbsp;&lt;/p&gt;</description>
      <category>삽질미학/Linux</category>
      <category>LUKS</category>
      <category>Ubuntu LUKS</category>
      <category>리눅스 LUKS</category>
      <category>우분투 LUKS</category>
      <author>상사꽃</author>
      <guid isPermaLink="true">https://hahaite.tistory.com/321</guid>
      <comments>https://hahaite.tistory.com/321#entry321comment</comments>
      <pubDate>Tue, 17 Oct 2023 11:09:46 +0900</pubDate>
    </item>
  </channel>
</rss>