[JavaScript] Call Stack & Execution Context

Dal.001·2022년 9월 27일
1
post-thumbnail

오늘은 JS에서 Call StackExecution Context에 대한 개념을 알아보려고 한다.


먼저 간단한 예시로 운을 띄워 보자

React-Native 빌드를 하면 실행 중에 다음과 에러를 마주할 때가 있다.

꼭 RN 개발이 아니더라도, 모바일이나 웹 개발자라면 한 번쯤 비슷한 에러 메세지를 접해봤을 것이라고 생각된다.

해당 에러는, 에러 메세지에도 나와 있듯, call stack이 넘쳐서 발생한 문제다.

보통은 재귀함수의 조건문에 논리적 헛점으로 인해 생기는 경우가 많다.

그렇다면 여기서 말하는 Call Stack은 무엇일까?


Call Stack

"Call Stack은 인터프리터가 여러 함수를 실행하는 중에, 현재 위치를 추적하도록 도와주는 메카니즘이다."

이렇게만 들으면 무슨 소리인지 잘 이해하지 못 할 수 있다.

간단한 예시와 함께 알아보자.

function first() {
	//part 1
	second();
    //part 2
}
function second() {
	console.log("second");
}

first();

위와 같은 코드가 있다고 할 때, 우리는 쉽게 실행 값을 예측 할 수 있다.
  1. 제일 먼저 first() 함수가 실행될 것이다.
    우리는 이때 이걸 first() 함수가 call stack list에 더해진다고 표현한다.

  2. first()함수의 part1이 실행된 후에 second() 함수가 실행된다.
    이때도 second() 함수가 call stack list에 더해진다.

  3. second() 함수가 모두 실행 된 다음, part2 부분이 실행 된 다음 first()가 call stack list에서 제거 되면서 실행이 마무리 된다.


이런 식으로 call stack은 어떤 함수가 현재 실행 중인지 파악하고, 어떤 순서로 실행 될 지를 판단하는데 사용된다.


call stack에는 실행 될 함수와 execution context가 저장 된다.

그럼 execution context에 대해 잠깐 알아보자

Execution Context

Execution Context -> 우리말로 하면 실행환경, 실행문맥 정도 되겠다.
말 그대로 실행할 코드의 "Context"를 지정하는 역할이다.

자바스크립트 엔진은 코드를 실행시키기 위해 3가지 정보를 알고 있어야 한다.

  1. 변수 객체 (Variable Object)
    변수, 함수 선언, parameter, argument 등 정보를 담는 객체를 말한다.

  2. 변수 scope (Scope Chain)
    JS 엔진이 렉시컬 스코프를 파악할 때 사용 된다. 특정 변수가 참조 되면, 스코프 체인 안에서 AO(Activation Object)를 차례로 검색해서 scope를 확인한다.

  3. this
    자신이 생성할 인스턴스를 가리키는 자기 참조 변수이다.

이와 관련 된 내용을 excution context가 포함하고 있다.


Execution Context는 크게 세 가지 종류가 있다.

1. global execution context

이름 처럼 전역에 있는 코드와 관련 된 context다.

앱 내에 있는 모든 JS 코드는 동일한 global execution context 내에서 실행된다.
global object를 생성하고 global object를 참조한다.

실행 시 제일 먼저 call stack에 추가 되며, 앱 종료할 때 call stack에서 없어진다.

2. functional execution context

함수가 실행되는 Context를 정의한다.

함수가 실행 할 때마다 새로 정의 되며, 함수 시작 시 call stack에 추가되고, 함수 종류 시 call stack에서 삭제 된다.

3. eval execution context

JS eval 함수를 실행 할 때 참조 되는 context 값이다.

eval 함수는 스트링으로 제공된 코드를 실제로 실행 시킨 후 return 값을 반환한다.
sql injection 처럼 해킹에 사용될 수 있기 때문에, 대부분 사용을 하지 않길 권고하고 있다.

하튼 이렇듯 새로운 코드를 실행해야할 context가 필요하기 때문에, eval execution context가 따로 존재한다.

eval 함수는 잘 사용하지 않기 때문에, 추가 설명은 생략하겠다.



execution context는 모두 실행 중에 두 가지 상태를 갖는다.

1. create phase

context가 처음 생성 되는 단계다.

Object를 생성

  • Global Execution Context : Global Object인 Window Object를 생성한다.
  • Functional Execution Context : arguments 객체를 생성한다.

This Binding

  • Global Execution Context : Window Object가 할당 된다.
  • Functional Execution Context : 함수가 호출되는 방식에 따라 다르게 할당 된다.
    함수가 객체 참조에 의해서 호출되면 해당객체로 설정되고, 그렇지 않을 경우 전역 객체(window)를 가르킨다. 또한 설정 모드에 따라서도 다른데, strict mode에서는 undefined를 가르킨다.

변수와 함수를 위한 메모리를 준비

  • 변수와 함수를 위해서 메모리를 준비한다.
  • 이때 var 변수에는 undefined를 할당하고, 함수는 메모리에 할당된다. (함수 hoisting이 진행된다.)

2. execution phase

실제로 실행 되는 단계다.

creation phase와 상태가 거의 비슷하지만, 변수가 할당된다는 점이 다르다.
JS 엔진이 코드를 한 줄씩 실행하며, 변수에 실제 값에 할당한다.

execution phase가 끝나면 Call Stack에서 Pop해서 제거한다.




CallStack에 함수 및 Execution Context가 추가되는 모습을 도식화 하면 다음과 같다.

<이미지 출처 : https://medium.com/sjk5766/call-stack%EA%B3%BC-execution-context-%EB%A5%BC-%EC%95%8C%EC%95%84%EB%B3%B4%EC%9E%90-3c877072db79>




참고 자료

https://developer.mozilla.org/en-US/docs/Glossary/Call_stack

https://dkje.github.io/2020/08/30/ExecutionContext/

https://medium.com/sjk5766/call-stack%EA%B3%BC-execution-context-%EB%A5%BC-%EC%95%8C%EC%95%84%EB%B3%B4%EC%9E%90-3c877072db79

https://velog.io/@dbfudgudals/javascript-context

profile
App/Server Software Engineer

0개의 댓글