programing

C/C++ 메인 함수의 파라미터는 어디에 있습니까?

coolbiz 2022. 7. 7. 23:41
반응형

C/C++ 메인 함수의 파라미터는 어디에 있습니까?

는 C/C++ 타입의 합니다.char*.

int main(int argc, char* argv[]){
  return 0;
}

argv는 의 is is is is is의 입니다.char*, 및 스트링을 가리킵니다.이자자 디디 ?디? ???아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 아, 네?

이들은 컴파일러의 매직으로 구현에 의존합니다.

C 표준(n1256)에서는 다음과 같이 기술되어 있습니다.

1 5.1.2.1
...
2 선언된 경우 파라미터는 기능은 다음과 같은 제약을 준수해야 한다.

  • argc 값은 음이 아니어야 한다.

  • argv[nullc]는 늘 포인터여야 합니다.

  • argc 값이 0보다 클 경우 argv[0] ~ argv[argc-1]의 어레이 멤버는 프로그램을 시작하기 전에 호스트 환경에 의해 구현 정의 값이 주어진 문자열에 대한 포인터를 포함해야 합니다.목적은 호스트 환경의 다른 곳에서 프로그램을 시작하기 전에 결정된 프로그램 정보를 제공하는 것입니다.호스트 환경에서 대문자와 소문자 모두로 된 문자열을 제공할 수 없는 경우, 구현에서는 문자열이 소문자로 수신되도록 해야 합니다.

  • argc 값이 0보다 클 경우 argv[0]가 가리키는 문자열은 프로그램 이름을 나타냅니다.호스트 환경에서 프로그램 이름을 사용할 수 없는 경우 argv[0][0]는 null 문자가 됩니다.argc 값이 1보다 클 경우 argv[1]에서 argv[argc-1]까지의 문자열이 프로그램 파라미터를 나타냅니다.

  • argc, argvargv 배열이 가리키는 문자열은 프로그램에서 수정할 수 있어야 하며, 프로그램 시작과 프로그램 종료 사이에 마지막으로 저장된 값을 유지해야 합니다.

마지막 글머리표는 문자열 값이 저장되는 가장 흥미로운 wrt입니다.힙이나 스택은 지정하지 않지만 문자열이 쓰기 가능하고 정적 익스텐트가 있어야 합니다.이것에 의해, 문자열의 컨텐츠가 배치되는 장소에 제한이 있습니다.다른 사람들이 말했듯이, 정확한 세부 사항은 구현에 따라 달라질 것입니다.

실제로는 컴파일러와 운영체제의 의존성을 조합한 것입니다. main()는 다른 함수와 는 C입니다.argc ★★★★★★★★★★★★★★★★★」argv플랫폼상의 컴파일러의 표준을 따릅니다.예를 들어 x86을 대상으로 하는 대부분의 C 컴파일러는 반환 주소와 저장된 베이스 포인터 바로 위에 스택에 있습니다(스택이 아래쪽으로 늘어납니다).되므로 x86_64는 레지스터로 됩니다.argc 있을 것이다%edi ★★★★★★★★★★★★★★★★★」argv 있을 것이다%rsi된 주요 입니다. 컴파일러에 의해 생성된 메인 함수의 코드가 스택에 복사되며, 이것이 나중에 참조되는 부분입니다.를 기능 할 수 하기 .main.

char*는 argv가 가리키는 문자이며 실제 문자 시퀀스는 어디에나 있을 수 있습니다.운영체제 정의 장소에서 시작되며 링커가 생성하는 프리암블코드에 의해 스택 또는 다른 장소에 복사될 수 있습니다. 해서 '비밀번호'의 합니다exec()링커에 의해 생성되는 어셈블러 프리암블을 확인합니다.

이 질문에 대한 답은 컴파일러에 의존합니다.즉, C규격으로 취급되지 않으므로 누구나 원하는 대로 구현할 수 있습니다.운영 체제에도 프로세스를 시작하고 완료하는 일반적인 방법이 없기 때문에 이는 정상입니다.

간단한 시나리오를 상상해 봅시다.

프로세스는 일부 메커니즘에 의해 명령줄에 기술된 인수를 수신합니다.argc는 프로그램(런타임의 일부)의 프로세스의 엔트리 포인트로 컴파일러가 배치한 부트스트랩 함수에 의해 스택에 푸시되는 int일 뿐입니다.실제 값은 운영 체제에서 가져오며, 예를 들어 힙의 메모리 블록에 쓸 수 있습니다.그런 다음 argv 벡터가 구축되고 첫 번째 위치에 대한 주소도 스택에 푸시됩니다.

그런 다음 프로그래머가 제공해야 하는 함수 main()을 호출하고 나중에(거의 즉시) 사용할 수 있도록 반환값을 저장합니다.히프의 구조가 해방되고 메인용으로 취득된 종료 코드가 운영체제로 내보냅니다.프로세스가 종료됩니다.

이들 파라미터는 다른 함수의 파라미터와 다르지 않습니다.아키텍처의 콜시퀀스에서 스택을 통과하기 위해 파라미터가 필요한 경우 해당 파라미터는 스택에 있습니다.x86-64와 같이 일부 파라미터가 레지스터에 들어가면 레지스터에도 들어갑니다.

~하듯이pmg언급, 시기main재귀적으로 호출됩니다.인수가 가리키는 것은 발신자에게 달려 있습니다.기본적으로 답은 의 최초 호출과 동일합니다.main단, '발신자'가 C의 실장/OS인 경우는 제외합니다.

UNIX-y 시스템에서는 다음 문자열이argv포인트:argv포인터 자체 및 프로세스의 초기 환경 변수는 거의 항상 스택 맨 위에 저장됩니다.

여기서 많은 다른 답변이 지적하듯이 컴파일러 구현이 인수를 메인에게 전달하기 위해 사용하는 정확한 메커니즘은 표준에서 지정되지 않습니다(컴파일러가 인수를 함수에 전달하기 위해 사용하는 메커니즘과 같습니다).엄밀히 말하면, 컴파일러는 이러한 파라미터에 도움이 되는 것을 전달할 필요도 없습니다.이는 값이 구현 정의되어 있기 때문입니다.그러나 이 두 가지 모두 특별히 도움이 되는 대답은 아닙니다.

일반적인 C(또는 C++) 프로그램은 '호스트형' 실행 환경(함수 사용)을 위해 컴파일됩니다.main()프로그램의 시작점이 호스트 환경에 대한 요구 사항 중 하나이기 때문입니다.중요한 것은 컴파일러가 운영체제에 의해 실행파일이 실행되었을 때 컴파일러의 런타임에 대한 제어가 아니라main()기능.런타임의 초기화 코드는 인수에 대한 메모리 할당을 포함하여 필요한 모든 초기화를 수행합니다.main()그 후 제어가 로 넘어갑니다.main().

인수 메모리main()는 힙에서 생성되거나 스택에 할당되거나(표준 C 코드에서 사용할 수 없는 기술을 사용), 스태틱하게 할당된 메모리를 사용할 수 있습니다.단, 이는 유연성이 떨어진다는 이유만으로 가능성이 낮은 옵션입니다.표준에서는 다음 명령어가 가리키는 문자열에 사용되는 메모리가 필요합니다.argv는 변경 가능하며 이러한 문자열에 대한 변경은 프로그램 수명 동안 지속됩니다.

실행이 도달하기 전에 주의하세요.main()프로그램 실행 환경을 설정하는 코드가 이미 상당히 많이 실행되었습니다.

인수 목록은 환경 변수와 비슷하지만 다른 프로세스 환경의 일부입니다.

보통 그들이 어디에 있는지 알 수 없다.

#include <stdlib.h>
#include <string.h>

int main(int argc, char *argv[]) {
  char **foo;
  char *bar[] = {"foo", "bar"};

  (void)argv; /* avoid unused argv warning */

  foo = malloc(sizeof *foo);
  foo[0] = malloc(42);
  strcpy(foo[0], "forty two");

  /* where is foo located? stack? heap? somewhere else? */
  if (argc != 42) main(42, foo); else return 0;

  /* where is bar located? stack? heap? somewhere else? */
  if (argc != 43) main(43, bar); else return 0;
  /* except for the fact that bar elements
  ** point to unmodifiable strings
  ** this call to main is perfectably reasonable */

  return 0;
  /* please ignore memory leaks, thank you */
}

실제 파라미터에는 접근할 수 있지만 실제 위치는 전혀 문제가 되지 않는다고 생각합니다.

언급URL : https://stackoverflow.com/questions/4196201/where-are-c-c-main-functions-parameters

반응형