커널 스택이 궁금합니다.

swunk의 이미지

리눅스 커널 스택에 대해서 궁금합니다.

1.커널 스택은 프로세스마다 하나씩 생성되는 건가요 ?
2.커널 스택에는 어떤 정보가 들어가게 되나요 ? (얼핏 알기로는 해당 프로세스에 인터럽트가 걸리면 이에 필요한 정보들을 커널 스택에 저장해 놓고 사용한다고 하던데요...)
3.프로세스 하나는 4기가의 가상 공간을 사용한다고 들었습니다. 이 중에서 0~3기가 까지는 응용프로그램에서 사용하는 공간이고 3~4기가는 커널이 사용하는 공간이라고 알고 있는데요...
여기서 3~4기가 공간과 커널 스택이 어떠한 연관 관계가 있나요?

고수님들의 답변 부탁드립니다.

가물가물의 이미지

오래되서 가물가물하지만...
근데 이런 질문은 어차피 리눅스에 국한된거라... 별 의미 없지않나 싶은데..

일단 추천책은 임베디드리눅스의 이해? 가물가물하다...
제목은 임베디드가 들어가는 데 임베디드랑 상관은 없고, 꽤 잼있습니다.

1. 커널 스택인데 프로세스마다 생기겠어요. 프로세스마다, 프로세스 고유의 스택을 사용합니다.
2. 정확히 모르겠네요. 죄송. 커널도 프로세스인데 프로세스 스택처럼 쓰겠죠.
이프로세스돌리다 다른 프로세스 돌릴려면 PDB던가? 아... 생각안나네.. 그런걸 저장하지 않을까요?
3. 그공간 안에 커널 스택이 있죠. 힙 스택 실행코드등이 들어있겠죠.

익명사용자의 이미지

알면 아주 좋습니다. 이런내용 하나하나에 관심을 가지면
프로그램 실력이 가파르게 상승하죠...

ssehoony의 이미지

커널 모듈 같인 것들도 마치 프로세스처럼 스택을 갖고 있는데 이런 모듈 같은 것들이 사용하는 스택을 커널 스택이라고 말하는 것 아닌가요?
리눅스의 경우 하나의 모듈의 스택은 4KB인가 그렇습니다.
프로세스의 스택의 기본 사이즈는 8메가 정도 하는 것으로 알고 있는데 많이 차이가 나죠.

headbang의 이미지

최근에 Linux Understanding Kernel 이란 책을 일부분 봤는데 어느 정보 아는 부분이라 지나가다 적어봅니다. 모든 설명은 80x86 아키텍처를 기준으로 합니다.

1. 커널 스택은 프로세스마다 하나씩 생성됩니다.
일반적인 프로세스는 User Mode 스택과 Kernel Mode 스택을 각각 하나씩 가지고 있습니다.
User Mode에서 Kernel Mode로의 전환은 시스템호출이나 인터럽트가 발생하면 일어납니다.
즉, esp 레지스터는 프로세스가 User Mode이면 User Mode 스택의 top을 가르키다가
Kernel Mode로 전환이 되면 Kernel Mode 스택의 top을 가르킵니다.

2. Kernel Mode 스택은 적어도 다음 두가지 목적으로 사용됩니다. 다른 사용처는 딱히 생각나지 않네요.
가. Kernel Mode로 전환된 프로세스는 언젠간 다시 User Mode로 되돌아가야 합니다.
따라서 User Mode로 전환하기위해 필요한 정보 중 일부를 저장합니다. (일부는 다른 곳에 저장합니다.)
나. Kernel Mode에서 함수를 호출하게 되면 그 함수의 지역변수는 Kernel Mode 스택에서 할당됩니다. (User Mode에서 함수를 호출하면 지역변수가 User Mode 스택에 할당되는 것과 같습니다.)
참고로 80x86 아키텍처에서 커널 스택으로 할당된 공간의 크기는 8KB로 고정되어있습니다. 프로세스 생성때 한번 할당되어 작아지지도 커지지도 않습니다. 따라서 커널에 있는 함수에서는 지역변수를 많이 할당하거나 재귀 함수 호출을 하면 좋지 않습니다.

3. 어떻게 설명드려야할 지 상당히 난해한 질문이군요.
커널은 주소 공간 3~4GB를 사용합니다. Kernel Mode 스택은 Kernel Mode에서만 사용되므로 커널 주소 공간에서 할당됩니다.
즉, User Mode 스택을 가르키는 esp 값을 읽어보면 0GB~3GB 사이의 값을 가지고 Kernel Mode 스택을 가르키는 esp 값을 읽어보면 3~4GB 사이의 값을 가지게 됩니다.

4. 기타

가. 프로세스의 User Address Space는 프로세스마다 각각 다르지만, Kernel Address Space는 모든 프로세스가 동일하게 봅니다. 즉, 프로세스 A와 프로세스 B의 특정 가상주소 (예를 들면 0xa0001000) 은 서로 다른 물리주소로 맵핑될 수 있습니다. 하지만 특정 커널 공간 주소 (예를 들면 0xc0001000) 는 모든 프로세스에서 동일한 물리주소로 맵핑됩니다.
이를 위해서 커널은 kernel master page table (swapper_pg_dir 변수가 가르킴)을 관리하고, 필요할 때마다 특정 엔트리를 kernel master page table에서 해당 프로세스의 page table에 복사를 합니다 -- 이런 작업은 Kernel Mode에서 페이지 폴트가 발생했을 때 페이지 폴트 핸들러가 수행합니다.

나. 시스템호출, 인터럽트 핸들러, 커널 모듈 등은 임의의 프로세스의 context를 이용합니다. 예를 들어, 프로세스 A가 User Mode에서 수행되고 있을 때 timer interrupt가 발생하는 경우 Kernel Mode로 전환하여 timer interrupt service routine을 수행하게 되는데 이때 프로세스 A의 page table과 Kernel Mode 스택을 빌어 쓰게됩니다.
Timer interrupt와 프로세스 A와는 별다른 연관이 없지만 interrupt 발생시점에 프로세스 A가 CPU를 점유하고 있었기 때문에 부하가 큰 context switch 등을 따로 하지 않고 프로세스 A의 context를 그대로 이용하는 것입니다. 다만 커널 모듈 등이 기능의 일부를 따로 커널 쓰레드를 생성하여 구현한 경우라면 그 커널 쓰레드의 context를 사용하겠죠.

swunk의 이미지

자세한 답변 감사합니다.
궁금했던 부분을 아주 벅벅 시원하게 잘 긁어 주셨어요...
다시한번 감사..

Jio Gim의 이미지

2019년에 봐도 가려운 부분을 잘 긁어주시네요...

AustinKim의 이미지

다른 분들이 이미 10여년 전에 훌륭한 답변을 달아 주셨는데 2019년인 지금 조금 더 덧붙히고자 합니다.

>1.커널 스택은 프로세스마다 하나씩 생성되는 건가요 ?

커널은 프로세스가 생성될 때 0x2000(32비트), 0x4000(64비트) 크기의 스택 공간을 할당합니다.
만약 init 이란 프로세스와 ksoftirq/0 프로세스가 있다면 각각 0x2000 사이즈 스택을 사용합니다.(32비트 기준)

>2.커널 스택에는 어떤 정보가 들어가게 되나요 ? (얼핏 알기로는 해당 프로세스에 인터럽트가 걸리면 이에 필요한 정보들을 커널 스택에 저장해 놓고 사용한다고 하던데요...)

프로세스가 실행하는 스택 공간에는 다음 정보를 확인할 수 있습니다.
1) 스택 최상단 주소에는 thread_info 구조체가 위치합니다. 이 구조체에서 프로세스 세부 실행 정보를 확인할 수 있습니다.
thread_info 구조체는 아키텍처(ARM, x86) 마다 정보(필드)가 다릅니다.
2) 스택 최하단 주소
: 유저 프로세스이면 유저 공간에서 실행 중인 레지스터 정보를 볼 수 있습니다.
3) 스택 최하단 주소 -> 스택 최상단 주소 방향
: 함수를 호출할 때 프레임 포인터 레지스터와 스택 주소를 확인할 수 있습니다.
: 함수 지역 변수에 저장된 값을 확인할 수 있습니다.

>3.프로세스 하나는 4기가의 가상 공간을 사용한다고 들었습니다. 이 중에서 0~3기가 까지는 응용프로그램에서 사용하는 공간이고 3~4기가는 커널이 사용하는 공간이라고 알고 있는데요...
>여기서 3~4기가 공간과 커널 스택이 어떠한 연관 관계가 있나요?

3~4 GB 바이트 내에 커널 스택이 있습니다.

(개인블로그)
http://rousalome.egloos.com

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.