[해결]shared object 내부에 있는 static variable의 초기화 시점?

hanseok의 이미지

안녕하세요 ..

최근 Disko(?)를 컴파일해서 테스트를 진행하고 있습니다.
s3c2440용..

작업하다 보니 문제점에 부딪혔습니다.
나름 고민 고민 하다가 의심 되는 부분이 이 부분입니다.

공개된 소스는 SO 로 만들어 집니다.
그런데 SO(shared object)안에 클래스의 멤버 변수가 static으로 선언되어 있습니다.

클래스를 생성하면서 인자값이 static 변수에 저장되는 형식입니다.
이곳에서 세그먼트 폴트를 나타내고 있습니다.

디버깅을 하다 보니.. SO안에 static 변수(클래스)가 존재하고
변수가 생성되는지 생성자에 프린트를 넣어보니..

인자값으로 들어오는 것 하나만 만들어지고
static으로 되어 있는 것은 생성이 안되고 있습니다.

만들어지지 않은 곳에 값을 넣으려고 하니.. 세그 폴트..

참고될만한 자료나? Shared object 내부의 static 변수, 함수에 대한 이야기좀 부탁드려 봅니다.

감사합니다.

ifree의 이미지

클래스를 정의하는 곳에서 static 멤버를 초기화 해주어야 storage 가 생기지 않나요?

class A
{
.
static int a;
.
};
A::a = 0;

hanseok의 이미지

class A {
....
};

---------
class B {
static A a;
public setA( A a) { this->a = a; }

}

-----------
A B::a;

------------
이렇게 적어 주면 되는 건가요?
헤더에는 적혀 있지 않구요..cpp에서 저와같이 구현되어 있습니다.

위의 코드는 모두 so로 들어가게 되구요.

g++ -fPIC
ld -share

이런것으로 컴파일 링크까지 완성한 상태에서
SetA 함수 안에서 this->a 을 호출하는 순간
세그먼트 폴트가 일어 납니다.

생성자에 프린트를 넣어서 확인해 본 결과
인자값으로 넘어가는 객체만 생성되고 static 은 생성자가 호출이 안되었습니다.

현재 arm-linux-g++ 3.4.3 를 사용중입니다.

잠이 들어야지만 꿈을 꿀수 있는것인가?
우리는 항상 꿈을 쫓아 가며 살아가는 사람들..

ifree의 이미지

서로 다른 cpp 파일에서 초기화가 되어서 생기는 문제 같네요.
링크 에러는 나지 않지만, static 멤버의 storage 확보가 setA 실행 이전에 된다는 보장이 없기 때문에 실행시 문제가 있을 것 같습니다.

drinkme의 이미지

class A가 어떤 문제가 있어서
할당이 안되는 것은 아닌가요?

말씀하신대로 구현하였다면, class B에 대해서는 문제가 없어보입니다.
member a에 대해서도 영역은 이미 BSS에 잡혀 있을 거고요.
실행이 되었다면,
a의 생성자 호출도 된 듯 합니다.

아마...
인자로 넘어온 a가 member a로 복사되면서 문제가 되는게 아닌가 싶습니다.

a의 복사생성자나 등등을 살펴보시는 것이 어떨까요?
gdb로 돌려보면
뭐하다가 죽었는지 알 수 있지 싶네요.

hanseok의 이미지

3.4.3 툴체인을 사용하여 위와 같은 문제가 발생하였었습니다.

클래스 안에 클래스가 존재하고
클래스안에 존재하는 static 변수가 있습니다. (이것이 shared library)

이런 경우 dl_open 에서 static에 대한 것을 모두 로드해 줘야 하는것이 옳바른 방법인듯 합니다
- 그런데 3.4.3에서는 이것이 로드가 되지 않았습니다. 결과적으로 이 변수를 사용하면 모두 세그폴트가 발생하였습니다.

툴체인(크로스컴파일러)을 eldk로 변경하며 gcc-4.0으로 변경하고 실행해 보니
시작한후 바로 생성자가 호출되는것을 확인하였습니다.

로드하면서 static 변수에 대한것을 초기화(?)-메모리공간의 할당- 해주는것이라 생각을 했습니다.

^^
정확한것은 아니지만 무언가 정확히 확인하지 못하였지만
툴체인 변경으로 일단은 해결을 했습니다.

답변 주신분들에게 감사드립니다.

잠이 들어야지만 꿈을 꿀수 있는것인가?
우리는 항상 꿈을 쫓아 가며 살아가는 사람들..

댓글 달기

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
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.