나는 몇 가지 장소를 보았습니다.여기그러나 아무도 스택 자체("작업"(프로세스/스레드)이 중첩된 호출 정보 등을 저장하는 위치)을 구현하는 데 사용되는 구조에 대해 자세히 설명하지 않았습니다. 연결된 목록입니까, 배열입니까, 아니면 다른 것입니까? 정보를 찾을 수 없는 것 같지만 다이어그램을 보면 항상 시작 부분에 힙이 있고 끝 부분에 스택이 있는 하나의 큰 메모리 블록(가상 메모리)으로 표시됩니다. 하지만 이것은 우리가 다루고 있는 가상 메모리이며, 페이징과 같은 주변의 다양한 데이터 구조를 가지고 있습니다. 그렇다면 문제는 이 모든 것 외에도 스택의 구체적인 구현이 무엇인지입니다. 나는 이것이 링크드 리스트임에 틀림없다고 생각하지 않을 수 없었다.
그 이유는 각각 자체 스택이 있는 여러 프로세스가 있는 경우 이를 어떻게 수행할 수 있기 때문입니다.
여기우리는 어느 정도 진전을 이루고 있는 것 같습니다:
각 프로세스에는 현재 커널에서 실행될 때 사용하는 자체 스택이 있으며, 이 스택의 크기는 8KB 또는 (64비트 시스템의 경우) 16KB 메모리입니다. 스택은 직접 매핑된 커널 메모리에 있으므로 물리적으로 연속되어 있어야 합니다.
답변1
스택은 실제로 배열입니다. 연속된 메모리에 여러 개의 단어가 포함되어 있지만 한 가지 중요한 제한이 있습니다. 한쪽 끝에서만 늘어나고 줄어들 수 있습니다(따라서 FILO - 선입후출). 이 역시 LIFO입니다.
어레이와의 중요한 차이점은 프로세서 스택이 논리적으로 프레임으로 나누어지고 (어레이와 달리) 각 프레임의 크기가 서로 다를 수 있다는 것입니다.
각 프레임에는 다음을 포함하여 함수 호출 시 저장해야 하는 콘텐츠가 포함되어 있습니다.
- 호출된 함수가 호출 함수를 계속하기 위해 점프하는 반환 주소입니다.
- 반환 값을 보관하는 공간입니다.
- 호출된 함수에 전달된 각 인수의 복사본입니다.
- 별도의 기능에서 레지스터 최적화가 방해되지 않도록 CPU 레지스터를 복사합니다.
각 수준의 모든 매개변수와 지역 변수에 동일한 이름을 사용하면서 함수가 어떻게 재귀적일 수 있는지 궁금해했다면 그 대답은 모두 현재 스택 프레임에 상대적인 주소를 가지고 있다는 것입니다.
스택 프레임 구조는 프로세서 아키텍처마다 다르게 정의되어 가장 자연스러운 저장 방법이 가능합니다. "Linux" 스택은 없습니다. Intel, AMD 및 Sparc에는 모두 고유한 정의가 있습니다. 미리 컴파일된 라이브러리를 다운로드할 수 있으며 로컬 컴파일러는 자신의 코드에서 이를 호출하는 방법을 알아야 합니다.
스택 자체도 범용 데이터 구조입니다. 예를 들어 C, SQL, XML 등 중첩된 블록 구성을 허용하는 언어로 소스 코드를 구문 분석하는 경우 자신이 속한 블록을 쌓는 것이 당연합니다. 이 작업을 수행하기 위해 프로세스 스택을 사용하고 싶지는 않을 것입니다. 구문 분석 중인 항목에는 재귀가 필요한 자체 코드가 아니라 블록 구조가 있습니다.
각 프로세스의 스택은 사용자 프로세스 메모리의 일부일 뿐입니다. 일반적으로 사용자 주소 공간의 범위는 -8MB에서 0, 60MB까지입니다. 스택은 -16에서 시작하여 아래쪽으로(점점 더 음수로) 증가합니다. 컴파일러 할당 전역 및 정적 메모리는 0에서 시작하여 위쪽으로 올라가며, 힙 할당은 고정된 메모리 이상으로 증가합니다. 코드는 보호상의 이유로 별도의 장소에 있습니다. 음수 주소 범위를 페이징된 메모리에 매핑해도 가상 스토리지 시스템에 해를 끼치지 않습니다.