slowbooktech   2년 전

안녕하세요, 아래 코드 중 A코드 로 제출해서 정답처리되었는데, 이해가 되지 않아 질문드립니다.

[A코드 설명]

A코드는 실제로 하나씩 키보드로 입력하는 과정에서 두수 입력을 받자마자 두 수의 합이 출력되지만 정답처리가 되었습니다. 즉, 예제에서는 입력을 전부 받고 한꺼번에 출력하는 것이 정답인데 제 코드대로라면 입력과 출력이 for문 안에서 번갈아 이뤄집니다.

[B코드 설명]

B코드는 위의 문제를 해결하기위해 한꺼번에 입력받고 출력하기 위하여 배열을 사용했으나 stackoverflow 오류를 맞닥뜨렸습니다. 배열에 너무 큰 값을 할당한 것이 원인인 것 같습니다.

[질문 요약]

원래대로라면 A코드는 문제에서 요구하는 것과 다른 결과값을 출력하고 있는게 맞죠? A가 정답처리된것은 file open 형식으로 정답 여부를 채점하기 때문일까요? 또, B코드는 왜 안되는 걸까요?

세 질문 중 하나만 답해주셔도 진심으로 감사합니다.

shjohw12   2년 전

문제에서 각 테스트 케이스 순서대로 출력을 요구하기 때문에 둘 다 맞는 코드입니다.

shjohw12   2년 전

두 번째 코드가 틀린 이유는 '\n'을 출력하지 않았기 때문입니다.

slowbooktech   2년 전

빠르게 답해주셔서 진심으로 감사합니다ㅠㅠ 첫번째 질문이 이해되었습니다!

두번째 코드는 \n을 삽입한 후여도 다음의 문구 및 페이지와 함께 stackoverflow 상태로 출력되지않습니다.

[문구]

0x00BF1CD9에(FOR.exe의) 처리되지 않은 예외가 있습니다.

0xC00000FD: Stack overflow(매개 변수: 0x00000000, 0x00CC2000).

[페이지]

page ,132
title chkstk - C stack checking routine
;***
;chkstk.asm - C stack checking routine
;
; Copyright (c) Microsoft Corporation. All rights reserved.
;
;Purpose:
; Provides support for automatic stack checking in C procedures
; when stack checking is enabled.
;
;*******************************************************************************

.xlist
include vcruntime.inc
.list

; size of a page of memory

_PAGESIZE_ equ 1000h


CODESEG

page
;***
;_chkstk - check stack upon procedure entry
;
;Purpose:
; Provide stack checking on procedure entry. Method is to simply probe
; each page of memory required for the stack in descending order. This
; causes the necessary pages of memory to be allocated via the guard
; page scheme, if possible. In the event of failure, the OS raises the
; _XCPT_UNABLE_TO_GROW_STACK exception.
;
; NOTE: Currently, the (EAX < _PAGESIZE_) code path falls through
; to the "lastpage" label of the (EAX >= _PAGESIZE_) code path. This
; is small; a minor speed optimization would be to special case
; this up top. This would avoid the painful save/restore of
; ecx and would shorten the code path by 4-6 instructions.
;
;Entry:
; EAX = size of local frame
;
;Exit:
; ESP = new stackframe, if successful
;
;Uses:
; EAX
;
;Exceptions:
; _XCPT_GUARD_PAGE_VIOLATION - May be raised on a page probe. NEVER TRAP
; THIS!!!! It is used by the OS to grow the
; stack on demand.
; _XCPT_UNABLE_TO_GROW_STACK - The stack cannot be grown. More precisely,
; the attempt by the OS memory manager to
; allocate another guard page in response
; to a _XCPT_GUARD_PAGE_VIOLATION has
; failed.
;
;*******************************************************************************

public _alloca_probe

_chkstk proc

_alloca_probe = _chkstk

push ecx

; Calculate new TOS.

lea ecx, [esp] + 8 - 4 ; TOS before entering function + size for ret value
sub ecx, eax ; new TOS

; Handle allocation size that results in wraparound.
; Wraparound will result in StackOverflow exception.

sbb eax, eax ; 0 if CF==0, ~0 if CF==1
not eax ; ~0 if TOS did not wrapped around, 0 otherwise
and ecx, eax ; set to 0 if wraparound

mov eax, esp ; current TOS
and eax, not ( _PAGESIZE_ - 1) ; Round down to current page boundary

cs10:
cmp ecx, eax ; Is new TOS
bnd jb short cs20 ; in probed page?
mov eax, ecx ; yes.
pop ecx
xchg esp, eax ; update esp
mov eax, dword ptr [eax] ; get return address
mov dword ptr [esp], eax ; and put it at new TOS
bnd ret

; Find next lower page and probe
cs20:
sub eax, _PAGESIZE_ ; decrease by PAGESIZE
test dword ptr [eax],eax ; probe page.
jmp short cs10

_chkstk endp

end

***********

읽어주셔서 감사합니다.

shjohw12   2년 전

두 번째 코드에 \n만 붙여서 제출하니 맞았다고 나옵니다.

http://boj.kr/2ec8ebfc6f1b4e14...

아마 작성자분 개발 환경에 스택 제한이 낮게 설정돼있어 그런 것 같습니다.

스택 제한을 신경쓰고 싶지 않다면 ans 배열을 전역으로 빼는 방법도 있습니다.

slowbooktech   2년 전

친절하고 빠른 답변 진심으로 감사드립니다. 2022년 잘 풀리는 한 해되시고 행복하세요!

질문이 해결되었습니다!

댓글을 작성하려면 로그인해야 합니다.