크래프톤 정글 TIL : 0912

lazyArtisan·2024년 9월 12일
0

정글 TIL

목록 보기
74/147

📚 Journal


잘하는 다른 동기 분에게 어떻게 문제에 접근했는지 물어봄. 시간이 없어서 많이 못 들음

  • 내가 사용할 수 있는 도구들이 뭐가 있는지 파악해야 함
  • 내가 지금 무엇을 왜 하는지 생각하고 해야지 아무 생각 없이 하면 안됨

코드 주석 + 디버깅 문구 스타일 따라해보기



📝 배운 것들


🏷️ ATA(IDE) 컨트롤러

  • ATA(IDE) 컨트롤러는 하드 디스크나 CD-ROM 드라이브와 같은 저장 장치를 제어하는 데 사용되는 장치입니다. 시스템이 저장 장치와 데이터를 주고받기 위해 필요한 명령어와 신호를 주고받는 역할을 합니다.

  • ATA-3는 ATA 표준의 세 번째 버전으로, 하드 디스크 드라이브 인터페이스의 개선 사항을 포함합니다.



🖥️ PintOS

🔷 User program


rox

rox-simple

open할 때 file_deny_write(real_file);
close할 때 file_allow_write(file);

두 줄 추가했더니 open하고 close가 터지기 시작함

순서 좀 바꾸고 보호 구문 추가해줌. 통과는 했는데 write 테케들이 통과 안 함.

실행 파일만 deny해야지 open할 때마다 deny하면 안된다고 함.

분명 헤더 파일도 추가했고 file을 멀쩡하게 사용하고 있는데 왜 -> 문법을 사용하면 에러를 일으키는 거지?

file.h에 struct file이 정의되지 않아서 그랬던 것. file.c에만 struct file이 정의돼있어 file.c 이외의 파일에선 struct file의 내부 요소를 사용할 수 없었다.

file.h에 struct file 정의 추가했더니 컴파일 오류.
file.c에 있는 struct file 정의 삭제했더니 해결됨.

왜 load에서 deny_write를 했는데 막상 write하려고 보면 deny_write가 0으로 초기화돼있는거지?

filesys.c\filesys_open()에서 dir_lookup으로

같은 파일이 아니기 때문. open할 때마다 아이노드만 갖고 파일은 다르다. 라고 생각했는데

내가 지금 디버깅 찍어서 어 왜 똑같지 분명 바꿔줬는데 라고 생각하는 부분이 inode...

file도 똑같은 것으로 판명됨. 진짜 뭐지?????

그러니까 file이 같은 file이긴 함. open을 하고 난 뒤에 file의 정보가 달라짐. filesys_open의 비밀을 알아내야 함.

file의 정보가 어딘가에서 유실된다는 현상의 원인 알아내기.

마음 가다듬고 침착하게 보니까 의외로 금방 찾음.
file_open할 때마다 deny_write를 false로 바꿔줌.

filesys_open 중에 idnoe_open도 호출되는데 이때 reopen이 아니면 deny_write_cnt가 initialize가 된다.

그런데 실행파일은 분명 이미 열려있는 파일일테도 indoe_reopen이 아니라 inode_open만 호출됨. (reopen은 inode->open_cnt++;만 하고 inode 그대로 반환함)

filesys_open을 하면 무조건 list_push_front(&open_inodes, &inode->elem);이 호출된다. 따라서 같은 파일을 연다면 open_inodes가 있을 테니 reopen을 해야 함.

근데도 안된다는 건 file에 대한 정보가 뭔가 복사가 안됐다거나?

일단 우회 방법을 떠올려보면 실행 파일인지 아닌지 확인한 다음 실행 파일이면 write를 안 하는 방법이 있는데 그게 가능한가?

단순히 deny_write의 위치의 문제라는건?

rox-simple이 시작된 후 open_inode 리스트가 초기화됐다.

할만큼 했다 답지 보자

우려했던 상황이 일어남
답지 봤는데 나랑 똑같은 곳에 deny_write 했음

그니까 다른 사람들은 open_inode 리스트가 멀쩡히 복사된다는 거임.

다시 생각해보니 그건 아님.

open_inode 리스트가 초기화 되는 건 맞는 절차임.
각 프로세스마다 열고 있는 파일의 리스트가 다를 테니까.

앞에서 봤듯이 file의 정보가 초기화되는 것도 정상임. 원래 함수가 그렇게 생겨먹음.

inode에 집착하지 말고 실행 파일에 deny_write를 먹이는 방법에 집중하자.

필요없는 inode 디버깅 다 지움.

bdgin 전후에 무슨 일이 벌어지는지 찾아볼 것.

ad-hoc 1 : 쓰레드에 실행 파일 이름을 담아둔 뒤 open할 때마다 실행 파일 이름하고 비교해서 deny_write 값
ad-hoc 2 : 파일 이름에 . 들어가면 실행 파일 아닌 걸로 간주

근데 이건 너무 말도 안되고

thread에 file struct를 추가해야되는구나.
이 방법이면 가능할듯.

"keep opening file"은 뭔 소린지 모르겠음

load할 때 실행 파일의 file struct를 쓰레드에 저장해두고
init_thread()할 때 해당 file의 deny_write를 true로 변경해주면 될듯!

아니 근데 load할 쓰레드에 실행 파일 정보를 건네줄 방법이 없지 않나?
일단 load에서 thread_current()에 넣어보기.

아 그렇게 하니까 page fault 뜸...
thread_current()에 넣는다고 해서 전달이 되는게 아님.

"keep opening file"이 대충 뭔 말인지 알 것 같음.
process.c에 전역 변수로 list를 선언해놓고
load 실행될 때마다 실행 파일 넣어주고
open할 때마다 실행 파일 리스트 훑으면서 같은 놈 있으면 deny_write true로 바꿔줘야됨

닫을 땐 어떡하냐 그러면
리스트 순회하면서 같은 놈이 있으면 삭제해줘야지 page fault 안 나는거임?
실행파일인지 아닌지는 간단하게 구분 불가능하니까?

/* An open file. */
struct file
{
    struct inode *inode; /* File's inode. */
    off_t pos;           /* Current position. */
    bool deny_write;     /* Has file_deny_write() been called? */
};

아니 주석 보니까 더 이 해결책이 납득이 안 감.
file_deny_write()로 해결을 해야된다는 건데
이건 file_deny_write()를 호출을 아예 안 하잖음?

뭔가 이상하다. 분명 다른 해결책이 있을거임.

open_inodes가 초기화되던 이유 : main에서 filesys_init을 호출하기 때문.

https://velog.io/@smilelee9/pintos-kaist-%ED%94%84%EB%A1%9C%EC%A0%9D%ED%8A%B8-System-call-6

답지를 또 봤는데 심기가 불편해짐.
여기선 thread_current()에 정보를 입력해놓고 전달시키려고 하고 있었음.
나는 전달한 거 접근하려고 하면 page fault나던데.
내가 접근한 방식이 문제였나?

그리고 일단 이 글에선 lg, sm 이것들 아무렇지도 않게 통과됨.
심적으로 너무 힘들다.



⚔️ 백준


📌 1065 한수

N=int(input())
cnt = 0
for i in range(1,N+1):
    num = i
    stack=[]
    while num > 0:
        stack.append(num%10)
        num = int(num/10)
    if len(stack) == 1:
        cnt+=1
        continue
    dv = stack[1] - stack[0]
    isHS = True
    while len(stack) > 1:
        last = stack.pop()
        blast = stack[-1]
        if (last - blast) != dv:
            isHS = False
            break
    if isHS:
        cnt+=1
print(cnt)

풀긴했는데 개억지로 품

import sys

input = sys.stdin.readline
# 1. N 입력받기
N = int(input().rstrip())
cnt = 0

# 2. 한수 개수 출력
for i in range(1, N + 1):
    temp = str(i)
    if len(temp) <= 2:
           cnt += 1
    else:
        if int(temp[1]) * 2 == int(temp[0]) + int(temp[2]):
            cnt += 1

print(cnt)

이 사람 좀 잘푼듯

등차수열의 성질을 이용했다.

0개의 댓글