[완료] 64비트 운영체제(with 64비트 CPU)에서 포인터 Length가 4바이트만 찍히는 현상

pchero의 이미지

안녕하세요.

오늘 이상한 현상을 보게 되어 글을 올리게 되었습니다.

테스트 서버로 64비트 CPU에 64비트 리눅스를 올려 사용중입니다.
프로그램을 컴파일 해서, 테스트하던 도중, Extern 의 선언 유무에 따라 printf로 나타나지는 주소값 이상때문에 코어가 생기는 현상을 겪었습니다.

정확히는 주소값이 8바이트에서 4바이트만 나타나집니다.
나타나는 주소값만 그러한 것이 아니라, 실제로 참조되는 메모리 번지때문에 오류가 생겨 코어가 생깁니다..

도대체 왜 이런 현상이 일어날까요?

# uname -a
Linux alldb 2.6.25 #1 SMP Thu Jun 12 06:00:39 KST 2008 x86_64 x86_64 x86_64 GNU/Linux

쿼드 코어로 processor 번호가 3번까지 같은 내용이 나옵니다.
# cat /proc/cpuinfo
processor : 0
vendor_id : GenuineIntel
cpu family : 6
model : 15
model name : Intel(R) Core(TM)2 Quad CPU Q6600 @ 2.40GHz
stepping : 11
cpu MHz : 1600.000
cache size : 4096 KB
physical id : 0
siblings : 4
core id : 2
cpu cores : 4
fpu : yes
fpu_exception : yes
cpuid level : 10
wp : yes
flags : fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush dts acpi mmx fxsr sse sse2 ss ht tm pbe syscall nx lm constant_tsc arch_perfmon pebs bts rep_good pni monitor ds_cpl vmx est tm2 ssse3 cx16 xtpr lahf_lm
bogomips : 4799.88
clflush size : 64
cache_alignment : 64
address sizes : 36 bits physical, 48 bits virtual
power management:

-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------

-- extern 선언했을때의 로그 --

extern AppExInfo* AttachAppExRep();

[17:14:08]주소값 Return 이전 [0x7fd654c80000]
[17:14:08]주소값 Return 이전 [0x7fd654c80000]
[17:14:08]주소값 리턴이후[0x7fd654c80000]
[17:14:08]주소값 리턴이후 pAppExRep[0x7fd654c80000]

-- extern 선언안했을때의 로그 ---

// extern AppExInfo* AttachAppExRep();

[17:17:29]주소값 Return 이전 [0x7fca03c0b000]
[17:17:29]주소값 Return 이전 [0x7fca03c0b000]
[17:17:29]주소값 리턴이후[0x3c0b000] [17:17:29]주소값 리턴이후 pAppExRep[0x3c0b000]

----------------------------------------------------------------------

프로그램 소스는 다음과 같이 구성되어 있습니다.
LogMessage 함수는 로그를 작성하는 함수입니다.

bb.c (실제 문제가 발생한 소스)

int main(void)
{
.....
pAppExRep = (AppExInfo*)AttachAppExRep();
LogMessage(1,"XXXXXXXXXXXX","주소값 리턴이후[%p] \n",(AppExInfo*)AttachAppExRep());
LogMessage(1,"XXXXXXXXXXXX","주소값 리턴이후 pAppExRep[%p] \n",pAppExRep);
...
}

aa.c (문제가 발생하는 함수가 들어있는 파일)

AppExInfo* AttachAppExRep(); // 원형 선언

AppExInfo* AttachAppExRep() {
LogMessage(1,"#######","주소값 Return 이전 [%p] \n",g_AppExInfoRep);
return (AppExInfo*)g_AppExInfoRep;
} // body 부분

nec의 이미지

의심되는 것이라면

extern 선언하면 다른 소스파일에 있는 해당 변수의 포인터를 가져오지만 extern 선언 안하면 해당 소스파일 내에 있는 변수로 가져올겁니다.

extern 유무는 컴파일, 링크과정에 영향이 있지요.
extern 선언되면 컴파일후 오브젝트 파일 내에 변수명 심볼정보가 남지만, 선언 안하면 해당 심볼 자체가 오브젝트파일 내에 없죠. 링크할때 심볼 참조를 못합니다.

** 지금 회사라 로그인 안하고 씁니다. 모니터링 하고 있어서 로그인하기 좀 찝찝함. (Necromancer)

pchero의 이미지

답변 감사합니다...ㅠㅠ
주말 내 신경 안쓰고 있다가 오늘 회사와서 확인을 했습니다.

문제가 되는 부분은 extern 선언의 유무에 따라 다르게 나타나는 결과값인데..

이상한 점은 나타나지는 메모리 번지 값이 4바이트 와 8바이트 두가지의 형태로 된다는 것입니다.

말씀주신 사항이 메모리 번지에도 영향이 미치는 것일까요?

---------------------------------
제일 왼쪽이 저입니다 :)

익명 사용자의 이미지

implicit declaration + I32LP64

pchero의 이미지

답변 감사합니다.

I32LP64 에 관한 내용을 아래의 링크에서 찾아보았습니다.

http://www.viva64.com/en/t/0028/

묵시적으로 int, long, ptr 등의 타입의 사이즈가 결정된다는 내용이었습니다.
그리고 http://www.viva64.com/en/t/0012/ 에서 더 많은 정보를 찾을 수 있었습니다.

그런데 위의 자료에서 64비트 시스템에서는 모두 ptr의 사이즈는 64비트로 나타나 있었습니다.
포인터의 사이즈가 왜 extern 선언의 유무에따라 바뀌게 되는지는 모르겠습니다...;;

---------------------------------
제일 왼쪽이 저입니다 :)

jick의 이미지

extern 선언을 안했으니 int를 돌려주는 함수로 간주되고, int는 거의 항상 4바이트이므로 포인터에서 4바이트만 짤라먹고 사용했을 겁니다.

이게 경고를 안내고 컴파일이 된다면 좀 심각한 상황인데요. -_-;; -W -Wall 주시고 전부 다시 컴파일해서 경고 나오는 건 다 잡으세요.

pchero의 이미지

감사합니다.

상상도 못했네요. 말씀대로 였습니다. 묵시적 리턴값 형변환으로 인해서 생긴 문제였습니다.
게다가 -W -Wall 옵션을 주고 다시 컴파일을 하니 문제가 명확해졌습니다.

warning: implicit declaration of function 'AttachAppExRep'
warning: cast to pointer from integer of different size

위와 같은 경고 메시지를 뿌려주었습니다.

감사합니다. 겨우 의문이 풀렸습니다. :)

---------------------------------
제일 왼쪽이 저입니다 :)

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.