C언어/잡학사전 8

[C언어] AIX 서버에서 char 타입 사용 시 반드시 주의할 점

C 개발을 하다 보면 char 타입의 변수로 return 값을 받을 일이 생긴다. 예를 들면 아래와 같은 코드다.#include char testFunction() { char ret; ... if(err > 0) { return -1; } return ret;}int main() { char a; a = testFunction(); if(a == -1) { printf("Error !!\n"); } return 0;} 겉보기에는 아무 문제없어 보이지만 AIX 서버에서 위의 코드를 실행하면 엄청난 문제가 발생한다. C는 기본으로 변수 타입을 선언하면 signed로 선언이 되며 이는 생략가능하다고 본능적(?)으로 알고 있을 것이다. 하지만 AIX 서버는 char 타입에 대해..

[C언어] 댕글링 포인터와 와일드 포인터 (Dangling pointer & Wild pointer)

와일드 포인터 (Wild Pointer) Wild Pointer(야생의 포인터). 단어의 의미 그대로 초기화가 안돼서 쓰레기값으로 채워진 포인터를 의미한다. 단어의 정의를 처음 볼 수도 있지만 포인터를 배울 때 가장 기본적으로 듣는 말이다. (포인터 변수는 NULL 초기화를 하는 것이 좋다.) 이유는 매우 간단하다. 개발자가 의도하지 않은 메모리 영역에 접근하여 SIGSEGV 같은 치명적인 오류가 발생할 수 있기 때문이다. 또한 Wild Pointer가 위험한 이유는 복잡한 비즈니스 코드에서 대부분의 포인터 예외처리는 NULL Check를 통해 이루어지는데, Wild Pointer의 경우 쓰레기값으로 채워져 있어 이러한 예외를 무력화하기 때문이다. 와일드 포인터 (Wild Pointer) 예외 처리 Wi..

[C/C++] 구조체 패킹 (struct packing)

패킹을 이해하기 전 패딩의 개념을 알아야 한다. https://hackerpark.tistory.com/entry/CC-%EA%B5%AC%EC%A1%B0%EC%B2%B4%ED%81%B4%EB%9E%98%EC%8A%A4-%ED%8C%A8%EB%94%A9-struct-class-padding [C/C++] 구조체(클래스) 패딩 (struct, class padding) 패딩 (padding) 패딩이란 CPU의 효율을 높이기 위해서 효율적으로 메모리를 사용하는 기법 중에 하나이다. (여기서의 효율이란 저장 공간 효율이 아닌 데이터 처리 속도 효율을 의미한다.) 어떤 식 hackerpark.tistory.com 패킹 패킹 (packing) 이란 패딩 규칙에서 기준이 되는 memory block 크기를 변경해서 ..

[C/C++] 구조체(클래스) 패딩 (struct, class padding)

패딩 (padding) 패딩이란 CPU의 효율을 높이기 위해서 효율적으로 메모리를 사용하는 기법 중에 하나이다. (여기서의 효율이란 저장 공간 효율이 아닌 데이터 처리 속도 효율을 의미한다.) 어떤 식으로 메모리를 사용하길래 효율적이라는 걸까? CPU의 데이터 처리 (매우 간략하게) 패딩을 설명하기 전에 CPU의 동작 방식에 대한 이해가 필요한데 너무 깊이 들어가면 이 글의 주제에서 벗어나기 때문에 간략하게 짚고 넘어가려고 한다. 요즘 대부분의 CPU 는 64bit 를 지원하는 x86_64 아키텍처를 사용하고 있다. 이것은 한 번의 CPU 연산으로 처리하는 최대 데이터의 크기가 64bit 즉, 64bit = 8byte 로 메모리에 적재된 데이터를 한 번에 8byte 까지 처리할 수 있다는 의미이다. CP..

[C언어] 함수 호출 규약 (Calling Convention, cdecl, stdcall, fastcall)

함수 호출 규약 ? 함수 호출 시 필요한 인자를 어떤 방법으로 전달할지(전달받을지), 함수 종료 시 데이터를 어떤 방식으로 전달할지(전달받을지), 스택을 어떤 방법으로 정리할지 정의해놓은 규칙을 의미한다. C언어를 제법 사용한 개발자 중에서도 함수 호출 규약 (Calling Convention) 이라는 단어를 처음 보는 사람도 있을 것이다. 이를 정확하게 이해하려면 프로세스의 구조와 스택, 어셈블리 언어에 대한 이해가 필요하다. 하지만 위의 이해를 모두 설명하면 끝이 없으니, 심도 깊은 글은 나중에 시간이 된다면 정리해보는 거로 하고 이 글에서는 간략하게 설명해볼까 한다. 스택(Stack) ? 프로세스 실행 시 필요한 여러 데이터들은 메모리에 적재되는데 프로세스의 메모리 영역에는 스택이라는 부분이 있다...

[C언어] 포인터 오프셋 (pointer offset)

C언어를 사용하면 포인터를 사용해야하는 빈도가 굉장히 높다. (사실 매번 쓴다.) 포인터의 활용은 상당히 다양하고 범위가 넓지만 그중에서도 오프셋을 계산하는 주제를 다뤄보려 한다. 포인터의 오프셋 ? 이 글에서의 포인터 오프셋은 포인터를 움직이면서 계산하는 것을 의미한다. 이러한 방법은 네트워크에서의 가변 데이터(패킷)을 다루거나 buffer 에 데이터를 적재할때 흔히 사용한다. 그렇다면 아래 그림에서의 offset 의 값은 무엇일까 ? pointer 가 0 에서 12 로 이동했으니 offset = 12 라고 생각하기 쉽다. 당연히 12 만큼 주소를 이동했지만 실제 코드 구현에서는 12 가 정답이 아닐 수 있다. #include #define MAX_BUF_SIZE 128 int m..

[C언어] 서식 지정자의 모든것 (서식문자)

서식 지정자 ? printf, scanf, sprintf, fprintf 등의 여러 API 에서 가변인자를 받아서 처리하기 위한 데이터 포맷이다. 가변인자를 처리하는 API 함수 내부에서 어떤 인자를 어떤식으로 처리할지 지정하기 위해서 사용한다. 잡학사전 여러 API 에서 가변인자를 서식 지정자를 통해 처리하는데 printf 와 scanf 만 비교해봐도 서식 지정자로 특정할 수 있는 자료형의 스펙이 조금씩 다르다. printf 는 타입을 전달받아 데이터를 출력하기 때문에 형변환(type casting) 및 형승격(type promotion) 을 통해 크기가 다른 타입에 대해서 유연한 메모리 처리가 가능하지만, scanf 는 포인터를 전달받아 입력받은 데이터를 저장하기 때문에 서식 지정자에 의존하여 메모리..

[C언어] int 와 long 은 무엇이 다를까? (short, short int, int, long int, long, long long)

역사 컴퓨터는 지금의 32bit 64bit 가 아닌 8bit 16bit 가 주도했던 시절이 있었다. 당연하겠지만 64bit 가 아니라 32bit 도 처리할 수 없는 컴퓨터가 많았던 시절이었다. 당시에(아직까지도) CPU 시장을 주도했던 인텔의 CPU 프로세서 80286(16bit) 의 출시가 1982년 , 80386(32bit) 의 출시가 1985년인걸 감안하면 C언어가 개발되고 32bit가 훨씬 나중에 나온것을 알 수 있다. C언어가 1972년에 출시된 언어인걸 생각해보면 당시 32bit는 이론상으로 존재했던 아키텍처였던 것이다. (지금은 64bit) C89 표준이 작성되던 시점에는 이미 x86이 개발되어있었지만 16bit가 여전히 대중적인(?) 아키텍처였다. 참고로 최초의 64bit CPU인 인텔의 ..

반응형