전체 글 (165)

09
09

우분투를 계속 쓰다 보니 운영체제는 잘 알게 되었습니다. 좋은...거죠...?

1. 문제의 발단

  • 우리는 일어나서 컴퓨터를 켜고, 잠들기 5분 전까지 휴대폰을 본다. (그러지 마세요. 수면 건강에 나쁩니다)
  • 그렇다면, 우리를 위해서 이렇게 열심히 일 해주는 기기들이 어떻게 일을 하는지 조금은 알고 이해해줄 필요가 있을 것이다.
  • 사실, 그것보다는 확실히 알고 더 잘 부려먹기 위함이 아닐까...?

2. 프로그램, 프로세스 그리고 스레드

  • 프로그램 : 평소에 많이 접하던. exe로 확장자명이 된 파일들이다. 파일들의 정보로 특정한 작업들을 할 수 있다.
  • 프로세스 : 프로그램이 실행되어서 컴퓨터에서 작업 중인 그 상태. 이때 작업하는 방식에 따라 동시성, 병렬성으로 나눌 수 있다.
  • 스레드 : 프로세스 안에서도 동시에 여러 가지 작업들이 동시에 진행되어야 할 때, 그 각각의 일들이 스레드로 진행되는 것이다.
    • 멀티 스레드?: 여러 가지 스레드가 동시에 진행된다. 이때는 전역 변수의 공간이나 동적으로 따로 할당된 Heap의 공간을 이용하여 작업을 진행하게 된다. 자연스럽게 프로세스 간의 통신보다 여러 스레드로 나눠 작업을 했을 때 처리량도 높고, 응답 시간도 줄어든다. 그래서 프로세스를 여러 개 만들어서 사용할 때 보다 스레드를 나눠 작업하는 것이 더 유리하다.
    • 물론 단점도 있다. Heap영역을 여러 스레드들이 공유하기 때문에, 동시에 스레드들이 같은 데이터에 접근을 하려고 하는 등의 상황이 있으면 결과에 영향을 미칠 수 있다. 그래서 작업의 순서를 정확히 해주는 '동기화' 작업이 필요하다.

3. 동시성과 병렬성

  • 동시성 : 하나의 프로세스의 코어에 스레드가 각각의 작업을 한 번에 하나씩 조금씩 하면서 각각의 작업을 넘어 다니면서 하게 된다. 이때, 각각의 작업들을 뛰어넘는 것을 'Context Switching'이라고 한다. 이는 몹시 빠르게 여러 작업들을 처리하기 때문에 여러 가지 작업들이 동시에 처리되는 것처럼 보인다.
  • 병렬성 : 하나의 프로세스에 코어가 여러 개 있어서 그 각각의 코어들이 스레드가 되고, 그들이 한꺼번에 각각의 작업들을 하게 된다. 컴퓨터의 CPU가 물리적인 문제로(발열 등) 발전에 한계치가 있으니까 그것을 넘어서 더 빠르게 작업들을 처리하려고 하다 보니 여러 개의  코어를 달아 버린 것이다.

4. 자바스크립트(v8) 엔진의 특징

  • v8 엔진? : 구글에서 개발한 오픈소스. 크롬이나 Node.js에서 사용하는 엔진이며, 자바스크립트 코드를 컴퓨터의 CPU가(정확히 말하면 마이크로 프로세서. 이들이 모여서 CPU가 된다) 알아들을 수 있도록 더 간단하게 만들어 주는 일을 하는 것이다.
  • 어떤 원리로 작동하길래 v8엔진이 좋다고 하나요?
    • 인터프리터 : 코드를 한 줄 한 줄 바로바로 기계어로 변환한다.
      • 장점: 속도가 빠르다. 바로 바로 나오니까 사용자 경험이 좋다.
      • 단점: 코드가 복잡해지면 점점 느려진다.
    • 컴파일러 : 코드의 전체를 읽고 기계어로 변환한다.
      • 장점: 최적화로 인해서 코드가 복잡해도 괜찮다.
      • 단점: 바로바로 결과가 나오지 않기 때문에 초기에 속도가 느리다.
    • 이때, v8엔진은 JIT(Just In Time) 컴파일러로 이 둘을 같이 사용한다.
      • 처음 코드를 보면 인터프리터에 전달해 코드를 한 줄씩 읽는다.
      • 읽으면서 최적화가 가능한 부분이 있으면 컴파일러로 넘겨 바로 최적화하며 읽는다.
    • 이렇게 둘의 장점을 동시에 사용하여 효율적으로 작업하게 된다.

5. 유니코드

  • 컴퓨터가 문자열을 읽는 원리
    1. 특정 문자를 누르면 전압의 차이로 0과 1로 표현된다. 즉, 2진수이다.
    2. 이때 하나의 0과 1이 1bit 씩 8개가 모여 8 bits가 되면 이를 1byte라고 한다.
    3. 이 1byte가 컴퓨터가 문자열을 받아들이는 최소 단위가 된다.
    4. 2의 8승인 255개 즉, 0부터 255이니까 총 256개의 데이터를 표현할 수 있게 된다.
  • 아스키코드
    • American Standard Code for Information Interchange의 줄임말이다.
    • 말 그대로 영어를 위한 문자 인코딩이다.
    • 컴퓨터가 문자열을 읽는 원리를 생각해보면, 특정 문자가 눌러졌을 때, bit로 표현된 숫자를 컴퓨터가 읽어서 아스키코드 표에서 찾아서 우리에게 문자로 보여주게 된다. 물론, 숫자 그대로도 보여줄 수 있다.
    • 아스키코드표에는 영어권 사람들을 위한 언어만 들어 있다. 만약, 영어 말고 다른 문자를 컴퓨터가 읽게 하기 위해서는 어떻게 해야 할까?
  • 그래서, 전 세계 모든 언어들을 다 표현할 수 있도록 만든 표를 '유니코드'라고 하는 것이다.
  • 하지만 언제 어떤 상황에 몇 byte로 맞게 읽어야 할까? 를 약속해 놓는 것이 '인코딩'이다. 이 방법을 문자를 저장해 줄 때 같이 보내줘야 똑바로 컴퓨터가 헷갈리지 않고 읽을 수 있게 된다.
  • UTF-8 vs UTF-16
    • UTF는 Universal Coded Character Srt + Transformation을 줄인 것으로 뒤에 오는 숫자는 bit를 말한다.
    • 이것도 역시나 문자 인코딩 방법 중 하나이다.
    • 웹에서는 대부분 UTF-8을 이용한다.

6. 비트맵과 백터

  • 갑자기 웬 이미지...?라고 생각할 수 있지만 이것도 컴퓨터가 이미지를 읽는 방식이므로 알아 두면 또 좋다.
  • 비트맵 : 픽셀 기반 즉, 아주 작은 점들이 모여 만든 이미지이다. 파일 크기가 크며, jpg, gif, png 등의 형식을 가진다.
    • 장점: 사진처럼 다양한 색깔의 표현이 가능하다.
    • 단점: 확대나 축소에 매우 취약하다.
  • 백터 : 점과 선으로 이루어진 이미지이다. 파일의 크기가 작고, 비트맵 형식으로 변환도 자유로운 편이다. 그래서 로고와 일러스트의 재작에 많이 쓰인다. svg 등의 형식을 가진다.
    • 장점: 확대 축소에 영향을 받지 않는다. 
    • 단점: 사진과 같은 정교한 색들의 표현은 한계가 있다.

7. 운영체제

이런식으로 유저와 컴퓨터가 상호작용을 하게 된다.

  • 컴퓨터 즉, 하드웨어들과 사용자 사이에 중계를 해주는 역할을 한다.
  • 운영체제가 없는 상황, 가끔 컴퓨터에 고장 나서 운영체제 선택이 안 되는 경우가 있다. 그럴 경우를 생각해 보자. 운영체제 없이 컴퓨터를 사용하려고 할 수도 있기는 하지만(현실적으로는 거의 불가능) 직접 선을 갈아 끼우는 등 하드웨어를 조종하여 사용을 할 수는 있겠지만 너무 힘들 것이다.
  • 이때, 직접 하드웨어를 조종하지 않아도 운영체제가 중간에서 둘의 대화를 물리적이지 않은 방법으로 도와줄 수 있다.
  • 컴퓨터 시스템의 처리 구조
    1. 유저가 필요한 작업을 요청한다.
    2. 응용프로그램이 작동하여 유저의 작업을 받아들이고 처리하려고 한다.
    3. 운영체제를 거쳐서
    4. 하드웨어가 직접 작업을 실행한다.
    5. 나온 결과들을 반대로 전달하면서 상호작용한다.

8. 가비지 컬렉션

  • 메모리에 필요 없는 자료들을 알아서 지워줘서 메모리 공간을 확보해 준다.
  • C언어와 같이 옛날에 쓰던 언어들에서는 가비지 컬렉션이 없다. 그럴 때는 메모리 누수가 생긴다.
    • 메모리 누수(memory leak): 코드를 짤 때, 비워줘야 할 공간을 실수로 안 비워줬을 때, 계속 쌓이게 되는 상황. 이는 피할 수 없다. 아무리 완벽하게 짠다고 해도 인간이 짠 코드이기 때문에 누수가 생길 수밖에 없다.
  • 하지만 상대적으로 최신의 언어들은 가비지 컬렉션이 이를 돕는다.

9. 가비지 컬렉션의 동작 원리

  • Mark-and-sweep : root와 연결되어 있는 변수들을 체크하고 나머지 체크되지 않은 변수를 다 지운다.
  • Reference counting: 각 변수들이 다른 변수들과 참조가 몇 번이 되는지를 계산해서 그 참조 횟수가 0이라면 지운다.
  • 하지만 그래도 완벽하게 메모리를 관리하지는 못 한다. 계발 환경에 따라 작동하는 방식이나 필요 없는 데이터들이 달라지기 때문이다.
  • 그래도 최대한 가비지 컬렉션이 잘 작동하게 하려면? 
    • 순환 참조 금지: 각각의 변수들이 서로를 참조하고 있다면 참조 횟수는 0이 될 수가 없게 된다.
    • 언어들 마다 각각의 누수 잡는 방법 알아 놓기: 언어들마다 누수를 잡는 방법이 존재한다. 이를 알고 알맞은 상황에 맞게 사용하여 누수를 막을 수 있다.

10. 캐시

  • 가져오는데 비용이 많이드는 사용빈도가 높은 데이터를 비용을 줄이기 위해 사용하기 편한 저장공간을 '캐시'라고 한다.
  • 웹 상황에서는 데이터 베이스에 저장된 정보를 매번 사용자가 요청할 때마다 가지고 올 때 비용이 발생하므로, 자주 방문하는 데이터들을 캐시에 저장해 놓으면 그 비용을 줄 일 수 있다.
  • 로컬 상황에서는 하드디스크에 저장된 정보를 매번 사용자가 요청할 때마다 가지고 올 때 비용이 발생하므로, 자주 사용하는 데이터를 램에 저장해 놓으면 그 비용을 줄일 수 있다. 하지만 램은 용량은 적은데 비싸기도 하다. 그래서 더 비용을 줄이고 더 자주 사용하는 작은 데이터들은 캐시 메모리에 저장해 놓아서 그 비용을 줄 일 수 있다.
  • 결론은 캐시에는 아주 작고, 자주 사용하는 중요한 데이터들을 저장하여 비용을 줄이기 위해 존제한다고 정리할 수 있겠다.

 

COMMENT
 
09
07

이것이 바로 한끗 차이가 아닐까요?

1. HTTPS?

  • 맞다. 우리가 주소창에 칠 때 맨 앞에 따라오는 놈이다.
  • Hyper Text Transfer Protocol 'Secure' Socket layer의 줄임말이다.
  • HTTP에 secure이 붙어서 더 안전한 녀석이다.

2. 작동방식으로 보는 HTTP vs HTTPS

  • HTTP는 문자 형식 그대로 정보를 보낸다. 그것이 비밀번호 같은 민감한 정보가 있다고 해도 그대로 보낸다.
  • 중간에 그것을 가로채면 그것을 바로 뺏겨버린다.
  • HTTPS는 그것을 '해싱' 하여 알 수 없는 텍스트로 바꿔서 정보를 보낸다.
  • 그것을 서버에서 해석해서 알아듣는다. 중간에 정보를 뺏겨도 해석할 방법을 모르기 때문에 상관없다.
  • 그리고 특별한 기관에서 '인증서'를 받은 곳에서만 이 HTTPS를 사용할 수 있기 때문에 비슷하게 만들어놓은 피싱 사이트인지를 확실히 알 수 있어서 신뢰하지 않는 사이트에서는 개인정보와 관련된 것들을 사용하지 않고 해킹을 막을 수 있다.
  • 그리고 확실하게 프로토콜 부분에 HTTP 형식인지, HTTPS 형식인지를 명시해 줘야 한다. 아니면 올바르지 않은 형식으로 정보를 읽어 오게 되므로 안된다. 
    • 기밀성(privacy) : 제삼자가 중간에서 정보를 가로챌 수 없게 암호화함
    • 무결성(integrity) : 정보가 중간에 조작되지 않는다.
    • 이 둘을 잘 지키고 있기 때문에 우리는 HTTPS가 더 안전하다고 말할 수 있다.
  •  

3. 인증서

  • 앞서 말했듯이, 브라우저가 접속한 서버가 정상적인 우리가 의도했던 서버라는 것을 보장하는 인증이다.
  • 인증된 기관(CA, Certificate Authority)에서 인증서를 발급하고, 그 인증기관들은 많지 않다. 그래서 받은 인증서를 인증기관들에게 확인하여 확실한 사이트 임을 보증하게 되는 것이다.
  • 주소창 위에 '자물쇠' 마크를 눌러보면 인증서의 상태를 확인할 수 있다. 티스토리 같은 경우 SSL Server Certificate라고 되어있다.

4. 어떻게 암호화를 할까?

  • 이들은 서로 각각의 '키'를 가지고 있다.
  • 이 키를 이용해 암호화를 하게 되고 키의 종류에 따라 해석하는 방식이 달라진다.
  1. 대칭키
    • 메시지를 보내는 쪽과 받는 쪽, 둘 다 똑같은 키를 가지고 있어서 해석하는 방식을 공유하여 암호화된 메시지를 해석해서 사용한다.
    • 이때, 키만 노출되지 않는다면 중간에 메시지를 가로채더라도 해석할 수 없다.
    • 하지만 결국, 한 번은 키를 보내는 쪽에 줘야 하기 때문에 이때 가로채면 막을 수가 없는 단점이 있다.
  2. 비대칭키
    • 두 개의 키를 가지고 해석을 하게 된다. 하나는 '공개키'로 이것은 누구나 볼 수 있으며 사용자가 사용하게 된다. 이는 모두에게 공개되어 있기 때문에 이 키 하나만 가지고는 아무것도 할 수 없다.
    • 하나는 '개인키'로, 서버에서 가지고 있다. 공개키로 암호화된 메시지는 서버에서 개인키를 이용해야만 다시 복호화할 수 있다.
    • 인증서와 같은 정보들은 서버에서 개인키로 암호화되어 사용자에게 보내지고, 이도 마찬가지로 개인키로 암호화된 내용은 사용자의 공개키로만 복호화가 가능하다. 그래서 인증서가 올바르지 않은 사이트에서의 정보를 해석하려고 하면 안 될 테니까, 우리는 안전한 사이트에서만 사용할 수 있다.

4. Hashing

  • 메시지를 암호화하는 알고리즘이다. 항상 고정길이를 리턴하고, 항상 input과 output이 일정하다. 즉, 순수 함수이다.
  • 그리고 해싱된 메시지는 복호화가 키를 모르고서는 사실상 불가능하다.
  • 물론 너무 간단하고 쉬운 경우는 이미 해싱된 결과들이 저장되어 해석할 수 도 있다. 이것을 레인보우 테이블이라고 한다.
  • 예를 들어, 1234, password 같은 걸로 비밀번호를 정해놓으면 아무리 암호화 해 놔도 다 뚫린다는 것이다.
  • 하지만 이는, 'Salt'를 이용하게 되면 더욱 안전하게 만들 수 있다.
  • 원래 있던 패스워드에서 자신만이 아는 문자를 추가해서 더 욱 복잡한 해쉬를 만들어서 서버는 솔트 값을 알고 그것까지 포함해서 해석하게 된다. 사용자마다 각기 다른 솔트 값을 가지고 있다면 더욱 좋다.

5. 결국, 어떻게 메시지를 주고받나요?

  1. handshake
    • 가장 먼저, 서버를 클라이언트가 신뢰하지 못하는 단계에서 클라이언트가 무작위의 데이터를 보낸다.
    • 그것의 응답으로 서버에서 생성된 무작위 데이터와 인증서를 보낸다.
    • 클라이언트는 받은 인증서를 브라우저에 내장된 CA들의 정보와 대조하며 신뢰할 수 있는 서버인지를 확인한다.
  2. 브라우저의 인증서 확인
    • 인증서에 있는 공개키를 알맞은 CA의 개인키로 복호화한다.
    • 이때 정상적인 서버에서 받은 인증서라면, 복호화가 올바르게 된다.
    • 하지만 아니라면 신뢰할 수 없는 사이트가 되는 것이다.
  3. 다시 서버로
    • 이제 비대칭키와 대칭키를 같이 사용한다.
    • 대칭키를 클라이언트와 서버는 공유하게 된다. 이때, 이 대칭키를 공유하는 방식이 비대칭키를 이용한 방식이다.
      • 만약, 계속 비대칭키 방식만 사용한다면 사이트를 이용할 때 주고받는 수많은 데이터들을 모두 비대칭 방식으로 만들면 시간이 너무 오래 걸린다. 
    • 아까. handshake 단계에서 만든 무작위 데이터, 받은 거, 자기가 만든 것 둘을 합쳐서 임시로 키를 만든다.
    • 이 임시키를 서버로 공개키로 보내진다. 이렇게 하면 양쪽에 동일한 대칭키를 만들게 된다.

6. 쿠키

  • 사이트를 방문할 때, 내 브라우저에 저장되는 작은 텍스트 정보들이다. 
  • 물론 나한테 저장된 정보기 때문에 정보를 수정하거나, 누군가에게 탈취당할 위험도 있다. 그래서 민감한 정보는 넣지 않는다.
  • 정말 중요한 정보들은 서버 측의 '세션'에서 관리하게 된다.
  • 이때, 사용자마다 작은 임시키를 쿠키에 넣어서 준다.
  • 이 사용자가 브라우저를 통해 사이트의 페이지들을 탐색할 때, 서버가 그 키를 보고 그 유저가 누구인지 알 수 있다.
  • 그래서 로그인이 안된 상태로 장바구니에 많은 아이템들을 담아 놓고 로그인을 하면 그대로 아이템들이 남아 있는 것이다!
  • 아이디 저장, 자동 로그인 같은 기능도 똑같다!
  • 그래서 쿠키를 지우면 자동 로그인이 풀리는 것이다.
  • 이때, '캐시'를 이용하면, 사용자가 자주 사용하는 데이터를 캐시에 담아, 가져오는데 비용이 많이 드는 정보를 사용자의 컴퓨터나 서버에 저장하여 그 비용을 줄일 수 있다.
COMMENT
 
09
03

무엇을 쓸지 싸우지 마세요. 결국 타노스 같은 엄청난 작업을 만나면 둘다 쓰게 될 태니까

1. SQL vs NoSQL

  • SQL은 일정한 형식을 가지고 데이터 베이스에 데이터를 저장하지만, NoSQL은 그 형식을 없애어서 더 자유롭게 자료를 저장할 수 있다는 것에 가장 큰 차이점을 가진다.
  • 그렇다고 한쪽이 무조건 좋다 라고 할 수 없다. 상황에 따라 맞는 방법을 사용하게 된다.

2. 둘의 차이점

  1. 수평적 확장성 vs 수직적 확장성 :
    • 수평적 확장성 => NoSQL: 서버의 갯수를 늘리면 무한대로 저장공간이 늘어날 수 있고, 응답의 속도도 크게 떨어지지 않는다. 그래서 큰 프로젝트를 할 때 더욱 어울린다. 물론 그만큼 사용되는 비용도 많이 늘어난다.
    • 수직적 확장성 => SQL: 하나의 노드에서 모든 것을 처리하게 된다. 그래서 계속 한 곳에 쌓인다고 표현하는 것 같다. 고성능의 장비 하나로 모든 것들을 처리하게 되기 때문에 비용은 적다. 하지만 처리속도에 그래도 무리가 간다.
  2. 쿼리 언어의 유무
    • 기본적인 언어는 비슷하게 사용된다. 하지만 NoSQL같은 경우, Relation Data 즉, 다양한 행과 열로 이루어진 테이블들이 계속해서 JOIN 되어 조밀하게 연결되어 있는 경우, 정확한 틀이 없어서 유지보수를 하기 복잡해진다. 
  3. 스키마의 유연성
    • 앞에서도 말 했듯이, 정확한 형태의 스키마를 이용해 데이터를 저장하게 되는 SQL과 더 자유롭게 스키마를 형성할 수 있는 NoSQL의 스키마의 유연성이 가장 큰 차이를 보인다.
    • 간단하게 말하면 NoSQL은 아무 JSON 문서도 다 데이터 베이스에 넣어버릴 수 있다. 모든 오브젝트 형식을 다 넣을 수 있기 때문이다. 이것이 자유다!

3. JSON vs BSON

  • JSON형식은 우리가 알고 있는 그 형식이다. {}로 묶은 각각의 필드들이 문자열처럼 따옴표로 이루어져 있고, 그에 대한 값을 : 뒤에 적어주며, 쉼표로 각각의 필드들을 구분해 준다.
{
	"id": 1,
    "name": "Tom"
    "age": 22
}
  • BSON은 JSON 처럼 텍스트 형태가 아니라 여러 가지 다양한 데이터 타입도 다 사용이 가능한 형식이다. JSON보다 읽는 속도가 빠르다. 하지만 JSON처럼 인간이 읽어서 내용을 파악하는 것은 무리가 있다.
{"hello": "world"} →
\x16\x00\x00\x00           // total document size
\x02                       // 0x02 = type String
hello\x00                  // field name
\x06\x00\x00\x00world\x00  // field value
\x00                       // 0x00 = type EOO ('end of object')
  • MongoDB에서는 둘 다 데이터 베이스에 넣을 수 있다. 하지만 MongoDB 내부에서는 BSON 형식으로 사용 중이다.

4. MongoDB

  • MongoDB는 NoSQL의 모델 중 하나이며, DOCUMET를 이용한 방식으로 데이터 베이스에 접근한다.
  • mySQL처럼 비슷한 명령어들이 있으며, 몇 가지는 다르다.

5. MongoDB에서 주로 사용하는 명령어

  • mongo : 인스턴스 활성화, 간단하게 시작할 때 사용한다고 생각하면 된다.
  • use 데이터 베이스 이름 : 사용할 데이터 베이스를 결정한다.
  • show dbs : 데이터 베이스의 목록을 본다.
  • db.stats() : 데이터 베이스의 상태를 본다.
  • db.shutdownServer() : 데이터 베이스를 끈다.
  • db.logout() : 데이터 베이스에서 로그아웃 한다.
  • db.createCollection(컬렉션 이름) : 컬렉션을 생성한다.
  • db. 컬렉션 이름.insert({json형식의 데이터}): 컬렉션에 데이터를 넣는다. => 만약 컬렉션을 만들지 않았어도 상관없다. 없으면 만들어 넣는다!
  • db. 컬렉션 이름.find(): 컬렉션을 확인한다.
  • db. 컬렉션 이름.remove({json형식에 맞게 적은 삭제할 document의 내용})
  • db.컬렉션 이름. drop():컬렉션을 지워버린다.

 

COMMENT
 
09
01

하나도 어지러운데 그 안에 또 넣는다구요...? 정상이 아니에요.

1. MVC?

  • Model View Controller을 줄여서 말한 것이다.
  • 어제의 글을 보면 마지막에 구조를 파악하는 것이 중요하다고 적었다.
  • 그 구조에는 일정한 패턴이 있었다. 그것이 바로 MVC이다!
  • 각각의 역할에 따라 파일들을 나누어 다른 역할을 하게 만든다.

2. 그림으로 보는 MVC

3. MVC의 구성요소

  1. Model : 데이터 베이스와 정보를 교환해서 Controller에게 정보를 주거나 요청을 받는다. 위의 그림에서는 MySQL이라고 되어 있다. 바로 View와 데이터를 교환하지 않는다.
  2. View : 사용자가 실제로 보는 화면을 구성한다. 무조건 Controller와 소통을 한다.
  3. Controller : View에서 일어나는 요청들을 Model로 주기 전에 데이터를 가공하며, 마찬가지로 Model에서 받은 데이터를 가공해 브라우저와 소통하는 진정한 연결다리가 된다.
COMMENT