Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Project 1 백업 및 커맨드 라인 파싱 구현 #26

Open
wants to merge 37 commits into
base: dev_sirloinbh
Choose a base branch
from

Conversation

sirloinbh
Copy link
Collaborator

No description provided.

sirloinbh and others added 7 commits December 13, 2023 05:07
strtok_r : 지정된 문자 (여기서는 공백)을 기준으로 문자열을 자르는 함수
process_exec에서 입력한 커맨드 전체가 file_name 인자로 넘어오면서 load함수를 호출
file_name을 공백 기준으로 자른 문자열을 argv 배열에 하나씩 넣어준다
argument_stack() : 인자값을 스택에 올리는 함수
유저 스택에 프로그램 이름과 인자들을 저장하는 함수이다.
parse : 프로그램 이름과 인자가 저장되어있는 메모리 공간
count : 인자의 개수
esp : 스택 포인터를 가리키는 주소

스택에 올리는 인자들은 배열 arg_list, token_count(=count), intr_frame
arg_address[128] : for문에서 스택에 담을 각 인자의 주소값을 저장하는 배열
process_exec()에서 넣어주는 arg_list로부터 값을 하나씩 꺼내서 if->rsp에 저장
if_->rsp는 user stack에서 현재 위치를 가리키는 스택 포인터이자 인터럽트 프레임 내 멤버
for문을 돌고 나면 fake address를 넣어주면서 해당 영역의 메모리를 0으로 초기화
hex_dump() : 스택에 저장된 값들을 16진수로 나타내는 함수
process_wait 함수에 무한루프를 추가
@sirloinbh sirloinbh self-assigned this Dec 13, 2023
@sirloinbh sirloinbh added the Feature 기능 구현 label Dec 13, 2023
@sirloinbh sirloinbh added this to the Project2 milestone Dec 13, 2023
halt() : power_off()함수를 호출하면서 pintos를 종료시키는 시스템 콜
exit() : 현재 실행중인 프로세스를 종료시키는 시스템 콜
exit_status : 종료상태, 자식프로세스가 사라지면서 부모에게 알림. 정상적 종료라면 0을 저장한다
create() : file을 만드는 시스템 콜. 파일을 만들기만 하고 열지는 않는다.
create를 실행하기 전에 해당 file이 유저 영역에 있는 file인지 확인해야 한다
파일 이름에 해당하는 파일을 제거하는 함수
open() : 파일을 열 때 사용하는 시스템 콜
file의 주소가 유효한 지 확인하고 현재 스레드의 fd 테이블을 순회하면서 fd를 저장한다.
fd가 유효하지 않으면 파일을 닫는다.
오류가 발생하면 -1을 반환한다
filesize() : 파일의 크기를 알려주는 시스템콜. 현재 스레드의 fd테이블에서 fd에 해당하는 파일을 불러온 다음 file_length 함수에 인자로 주어서 리턴
buffer : 읽은 데이터를 저장할 버퍼의 주소값
size : 읽을 데이터의 크기
fd 값이 0일 때는 표준입력이기 때문에 input_getc() 함수를 이용하여 키보드의 데이터를 읽어 byte에 저장한다.
입출력은 커널 영역에서 진행되기 때문에 lock을 사용해서 interupt를 발생시킨다.
write() : 열린 파일의 데이터를 기록하는 시스템 콜
마찬가지로 fd값이 1일 때는 표준 출력이기 때문에 1일시 putbuf()함수를 사용하여 버퍼에 저장된 데이터를 화면에 출력한다
입출력은 커널 영역에서 진행되기 때문에 lock을 사용해서 interupt를 발생시킨다.
seek() :  열린 파일의 위치(offset)로 이동하는 시스템 콜
tell() : 열린 파일의 위치를 알려주는 시스템 콜
close() : 열린 파일을 닫는 시스템 콜. 파일을 닫고 fd를 제거한다
파일 삭제는 커널 영역에서 진행되기 때문에 lock을 사용해서 interupt를 발생시킨다.
check_address() : 해당 주소값이 주소 영역에 있는 주소값인지 확인하는 함수
시스템 콜이 접근할 수 있는 주소가 제한되어있기 때문에 유저 영역을 벗어날 경우 비정상 접근이라고 판단해 exit(-1)을 호출해서 프로세스를 종료한다
exec() : 인자로 받은 파일을 실행하는 함수
새로운 프로세스를 생성하는 것이 아니며 fork가 자신의 복사본을 생성해서 실행한다면, exec은 자신의 복사본이 아닌, 전혀 다른 프로그램을 실행한다
file_name을 copy하는 이유는 process_exec()에서 process_cleanup()을 할 때 해당 file_name의 문자열의 물리적 메모리와의 매핑 정보를 담은 Page Table도 같이 지워지기 때문이다.
wait() : 자식 프로세스가 올바르게 종료됐는 지 확인한 후 모두 종료될 때까지 대기하는 함수. 자식프로세스의 종료 상태를 반환한다
fork() : 현재 프로세스를 복사한 새 자식 프로세스를 만드는 시스템 콜
자식 프로세스는 부모 프로세스와 다른 PID를 갖는다.
fork의 반환값으로 부모 프로세스는 자식 프로세스의 PID를, 자식 프로세스는 0을 반환받는다
1. 기다려야 하는 자식 프로세스의 tid를 인자로 받는다
2. 자식 프로세스의 wait_sema를 Down해 주고 block된다. 자식 프로세스가 sema_up()함수를 호출해서 명시적으로 깨우지 않으면 부모 프로세스는 계속 잠들어 있는다.
3. 자식 프로세스가 실행되어 작업을 한 후, 종료되기 직전에 부모 프로세스를 깨우고 자신을 block한다. 부모 프로세스는 자식 프로세스의 exit_status를 받아온다
4. 부모 프로세스는 child_list에서 자식 프로세스를 지우고 block되어있던 자식프로세스를 깨워 제대로 종료될 수 있도록 한다.
5. 종료된 자식 프로세스의 exit_status를 반환한다.
함수에 세마포어를 추가해서 자식 프로세스가 종료되었을 때 부모 프로세스를 깨울 수 있게 구현
메모리가 동적으로 할당된 페이지를 free해줌으로써 메모리 누수를 방지한다
__do_fork() : 현재 실행되고 있는 부모 프로세스를 자식 프로세스에 복제하는 함
자식이 fork를 완료할 때까지 block되어 있다가 자식의 fork가 완료되면 새롭게 생성된 자식 프로세스의 pid를 반환한다
if_ :시스템 콜을 부른 부모 프로세스의 인터럽트 프레임. 시스템 콜 핸들러 함수에 인자로 전달된다.
시스템 콜을 부르기 전의 부모 프로세스의 레지스터 값들이 필요하기 때문에 부모 프로세스의 인터럽트 프레임을 복사해서 사용한다.
1. 부모의 CPU문맥인 intr_frame 값을 복사하고 RAX에 0을 저장한다.
2. 자식 프로세스는 RAX의 값을 0으로 설정하고, 부모 프로세스는 나중에 return tid;를 통해 자식의 PID를 RAX 값으로 설정한다.
3. 자식 프로세스는 부모 프로세스의 FDT( 파일 디스크럽터 테이블)의 원소들을 순환하면서 파일을 복사한 다음, 자신의 FDT를 채운다. fdt와 그에 매핑되는 파일들도 모두 똑같이 복사한다.
4. 자식의 fork가 끝날 때 잠들어있던 부모 프로세스를 깨운다.
5. 마지막으로 if_의 값들을 모두 레지스터에 넣음으로써 자식 프로세스를 실행시킨다.
1. is_kernel_vaddr()함수를 사용해서 주소 va가 커널 주소 공간에 속하는 지 확인한다음 커널 페이지인 경우 복사 중지
2. pml4_get_page() 함수를 사용해서 부모 프로세스의 페이지 테이블에서 가상주소 va에 해당하는 페이지를 가져온다.
3. palloc_get_page() 함수를 사용해서 자식 프로세스를 위한 새 페이지를 사용자 모드 페이지로 할당.
4. memcpy를 사용하여 부모 페이지의 내용을 새 페이지로 복사. is_writable(pte)를 사용하여 부모 페이지가 쓰기 가능한지 확인.
5. pml4_set_page() 함수를 사용해서 자시 프로세스의 페이지 테이블에 새 페이지를 추가한다.
자식 프로세스는 부모 프로세스와 별도로 물리 메모리 공간을 가진다. 다만, 부모와 자식 프로세스의 가상 메모리 주소가 같으면 같은 물리 메모리 공간에 정보가 mapping된다.
table : 현재 스레드의 파일 디스크럽터 테이블(fdt)를 가리키는 이중 포인터
현재 스레드가 작동중이면 file_close로 닫는다
테이블을 순환하면서 원소 파일들을 모두 file_close로 닫은다음, 배열의 공간을 NULL로 바꾼다
변수명을 잘못 적은 것을 바로쓴다. pfd ->fdt
get_child_process : 현재 실행중인 스레드(부모 프로세스)의 자식 프로세스 목록에서 특정 프로세스 식별자(PID)를 가진 자식 스레드를 찾아 반환하는 기능을 하는 함수
현재 스레드와 자식 스레드를 참조한 다음 while 문으로 자식 스레드를 탐색한다. PID일치를 검사한 다음 리턴한다.
dup2() : oldfd가 유효한 지 확인하고 newfd에 복사하는 함수
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Feature 기능 구현
Projects
Status: No status
Development

Successfully merging this pull request may close these issues.

1 participant