質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
87.20%
OpenGL

OpenGLは、プラットフォームから独立した、デスクトップやワークステーション、モバイルサービスで使用可能な映像処理用のAPIです。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。

受付中

malloc(): invalid size (unsorted) の原因が知りたい。

samidare_chan
samidare_chan

総合スコア142

OpenGL

OpenGLは、プラットフォームから独立した、デスクトップやワークステーション、モバイルサービスで使用可能な映像処理用のAPIです。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。

0回答

-5評価

0クリップ

633閲覧

投稿2022/05/03 06:29

編集2022/05/04 00:06

提示コードなのですが画像を読み込むコードで以下のコンソール画面の実行時エラーが発生します。なぜinvalid sizeになるのでしょうか?prite = FrameWork::LoadTexture("asset/texture/brickChip.png"); をコメントアウトすると実行できるためこの関数が原因なのでは事実です。メモリ確保エラーのメッセージと思われます。

確認したこと

逐次実行でFrameWork::LoadTexture()関数が原因であることが判明 ※コメントアウトして実行して確認
画像ファイルが読み込まれていること。画像ファイルが存在していることを確認
参考サイトAより
日本語訳

エラーを検索すると、Cプログラミングでよくあるエラーであることがわかります。プログラムが割り当てられたメモリ(文字列や動的配列、または自分で割り当てたもの)で範囲外になっていることを意味しているようです。(ただし、-exxがキャッチしない場合は、おそらく配列ではありません。) gdbなどのデバッガーで詳細を確認できるはずです。 -gを指定してコンパイルし、gdbにロードしてプログラムを「実行」すると、その時点で停止し、行番号が表示されるか、バックトレース(「bt」)してどの関数を確認できるかがわかります。コードが実行されていました。

とあるのですがbtコマンドでトレースしました。
LoadTexture()関数の//stbi_image_free(texture.data);のコメントアウトを解除してDeleteTexture() 関数の//stbi_image_free(texture.data);をコメントアウトするとdouble free or corruption (!prev) というエラーが出ます。

参考サイトA:https://www.freebasic.net/forum/viewtopic.php?t=29372#:~:text=Re%3A%20malloc()%3A%20invalid%20size%20(unsorted)&text=It%20looks%20like%20it%20means,able%20to%20tell%20you%20more.
参考サイトB: https://stackoverflow.com/questions/2902064/how-to-track-down-a-double-free-or-corruption-error

コンソール画面
$ ./Game ああ ああ malloc(): invalid size (unsorted) 中止 (コアダンプ)
gdbデバッグ画面
(gdb) run Starting program: /home/shigurechan/prg/2D_GameProject/Game/Game [Thread debugging using libthread_db enabled] Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1". [New Thread 0x7fffece88700 (LWP 37573)] [New Thread 0x7fffe7fff700 (LWP 37574)] ああ ああ malloc(): invalid size (unsorted) Thread 1 "Game" received signal SIGABRT, Aborted. __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:50 50 ../sysdeps/unix/sysv/linux/raise.c: そのようなファイルやディレクトリはありません. (gdb) bt #0 __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:50 #1 0x00007ffff79ab859 in __GI_abort () at abort.c:79 #2 0x00007ffff7a1629e in __libc_message (action=action@entry=do_abort, fmt=fmt@entry=0x7ffff7b40298 "%s\n") at ../sysdeps/posix/libc_fatal.c:155 #3 0x00007ffff7a1e32c in malloc_printerr (str=str@entry=0x7ffff7b42a50 "malloc(): invalid size (unsorted)") at malloc.c:5347 #4 0x00007ffff7a210e4 in _int_malloc (av=av@entry=0x7ffff7b75b80 <main_arena>, bytes=bytes@entry=10048) at malloc.c:3736 #5 0x00007ffff7a232c9 in __GI___libc_malloc (bytes=10048) at malloc.c:3066 #6 0x00007ffff7db4b39 in operator new(unsigned long) () from /lib/x86_64-linux-gnu/libstdc++.so.6 #7 0x0000555555578a97 in __gnu_cxx::new_allocator<std::_Sp_counted_ptr_inplace<Generate_Dungeon, std::allocator<Generate_Dungeon>, (__gnu_cxx::_Lock_policy)2> >::allocate (this=<optimized out>, __n=1) at /usr/include/c++/9/ext/new_allocator.h:102 #8 std::allocator_traits<std::allocator<std::_Sp_counted_ptr_inplace<Generate_Dungeon, std::allocator<Generate_Dungeon>, (__gnu_cxx::_Lock_policy)2> > >::allocate (__a=..., __n=1) at /usr/include/c++/9/bits/alloc_traits.h:443 #9 std::__allocate_guarded<std::allocator<std::_Sp_counted_ptr_inplace<Generate_Dungeon, std::allocator<Generate_Dungeon>, (__gnu_cxx::_Lock_policy)2> > > (__a=...) at /usr/include/c++/9/bits/allocated_ptr.h:97 #10 std::__shared_count<(__gnu_cxx::_Lock_policy)2>::__shared_count<Generate_Dungeon, std::allocator<Generate_Dungeon>>(Generate_Dungeon*&, std::_Sp_alloc_shared_tag<std::allocator<Generate_Dungeon> >) (__a=..., __p=<optimized out>, this=<optimized out>) at /usr/include/c++/9/bits/shared_ptr_base.h:677 #11 std::__shared_ptr<Generate_Dungeon, (__gnu_cxx::_Lock_policy)2>::__shared_ptr<std::allocator<Generate_Dungeon>>(std::_Sp_alloc_shared_tag<std::allocator<Generate_Dungeon> >) (__tag=..., this=<optimized out>) at /usr/include/c++/9/bits/shared_ptr_base.h:1344 #12 std::shared_ptr<Generate_Dungeon>::shared_ptr<std::allocator<Generate_Dungeon>>(std::_Sp_alloc_shared_tag<std::allocator<Generate_Dungeon> >) (__tag=..., this=<optimized out>) at /usr/include/c++/9/bits/shared_ptr.h:359 #13 std::allocate_shared<Generate_Dungeon, std::allocator<Generate_Dungeon>>(std::allocator<Generate_Dungeon> const&) (__a=...) at /usr/include/c++/9/bits/shared_ptr.h:702 #14 std::make_shared<Generate_Dungeon> () at /usr/include/c++/9/bits/shared_ptr.h:718 #15 Stage::Stage (this=0x555555e72a10) at source/Stage.cpp:10 #16 0x000055555557729a in __gnu_cxx::new_allocator<Stage>::construct<Stage> (this=<optimized out>, __p=0x555555e72a10) at /usr/include/c++/9/new:174 #17 std::allocator_traits<std::allocator<Stage> >::construct<Stage> (__a=..., __p=0x555555e72a10) at /usr/include/c++/9/bits/alloc_traits.h:483 #18 std::_Sp_counted_ptr_inplace<Stage, std::allocator<Stage>, (__gnu_cxx::_Lock_policy)2>::_Sp_counted_ptr_inplace<>(std::allocator<Stage>) (__a=..., this=0x555555e72a00) at /usr/include/c++/9/bits/shared_ptr_base.h:548 #19 std::__shared_count<(__gnu_cxx::_Lock_policy)2>::__shared_count<Stage, std::allocator<Stage>>(Stage*&, std::_Sp_alloc_shared_tag<std::allocator<Stage> >) (__a=..., __p=<optimized out>, this=<optimized out>) at /usr/include/c++/9/bits/shared_ptr_base.h:679 #20 std::__shared_ptr<Stage, (__gnu_cxx::_Lock_policy)2>::__shared_ptr<std::allocator<Stage>>(std::_Sp_alloc_shared_tag<std::allocator<Stage> >) (__tag=..., this=<optimized out>) at /usr/include/c++/9/bits/shared_ptr_base.h:1344 #21 std::shared_ptr<Stage>::shared_ptr<std::allocator<Stage>>(std::_Sp_alloc_shared_tag<std::allocator<Stage> >) ( __tag=..., this=<optimized out>) at /usr/include/c++/9/bits/shared_ptr.h:359 #22 std::allocate_shared<Stage, std::allocator<Stage>>(std::allocator<Stage> const&) (__a=...) --Type <RET> for more, q to quit, c to continue without paging-- at /usr/include/c++/9/bits/shared_ptr.h:702 #23 std::make_shared<Stage> () at /usr/include/c++/9/bits/shared_ptr.h:718 #24 Game::Game (this=0x55555578d2c0) at source/Game.cpp:9 #25 0x0000555555576f47 in __gnu_cxx::new_allocator<Game>::construct<Game> (this=<optimized out>, __p=0x55555578d2c0) at /usr/include/c++/9/new:174 #26 std::allocator_traits<std::allocator<Game> >::construct<Game> (__a=..., __p=0x55555578d2c0) at /usr/include/c++/9/bits/alloc_traits.h:483 #27 std::_Sp_counted_ptr_inplace<Game, std::allocator<Game>, (__gnu_cxx::_Lock_policy)2>::_Sp_counted_ptr_inplace<>(std::allocator<Game>) (__a=..., this=0x55555578d2b0) at /usr/include/c++/9/bits/shared_ptr_base.h:548 #28 std::__shared_count<(__gnu_cxx::_Lock_policy)2>::__shared_count<Game, std::allocator<Game>>(Game*&, std::_Sp_alloc_shared_tag<std::allocator<Game> >) (__a=..., __p=<optimized out>, this=<optimized out>) at /usr/include/c++/9/bits/shared_ptr_base.h:679 #29 std::__shared_ptr<Game, (__gnu_cxx::_Lock_policy)2>::__shared_ptr<std::allocator<Game>>(std::_Sp_alloc_shared_tag<std::allocator<Game> >) (__tag=..., this=<optimized out>) at /usr/include/c++/9/bits/shared_ptr_base.h:1344 (gdb)

cpp

Stage::Stage() { sprite = FrameWork::LoadTexture("asset/texture/brickChip.png"); dungeon = std::make_shared<Generate_Dungeon>(); dungeon->GetStage(grid); //ダンジョン生成 }

cpp

// ##################################### テクスチャをロード ##################################### FrameWork::Texture FrameWork::LoadTexture(const char* fileName) { Texture texture; glm::ivec2 size; int channel; unsigned char* data = NULL; data = stbi_load(fileName, &size.x, &size.y, &channel, 0); texture.size = size; if (data == NULL) { std::cerr << "画像が見つかりません: " << fileName << std::endl; assert(0); } glGenTextures(1, &texture.ID); //テクスチャIDの生成 glBindTexture(GL_TEXTURE_2D, texture.ID); // IDバインド //テクスチャ生成 if (channel == 4) { glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, size.x, size.y, 0, GL_RGBA, GL_UNSIGNED_BYTE, data); } else if (channel == 3) { glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, size.x, size.y, 0, GL_RGB, GL_UNSIGNED_BYTE, data); } else if (channel == 2) { glTexImage2D(GL_TEXTURE_2D, 0, GL_RG, size.x, size.y, 0, GL_RG, GL_UNSIGNED_BYTE, data); } else if (channel == 1) { glTexImage2D(GL_TEXTURE_2D, 0, GL_RED, size.x, size.y, 0, GL_RED, GL_UNSIGNED_BYTE, data); } else { std::cerr << "未対応の形式のチャンネル数です: " << fileName <<" "<< "チャンネル数: "<<channel<< std::endl; assert(0); } // テクスチャの補間設定 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE); glBindTexture(GL_TEXTURE_2D, 0); texture.data = data; printf("ああ\n"); //stbi_image_free(texture.data); return texture; } // ##################################### テクスチャを削除 ##################################### void FrameWork::DeleteTexture(FrameWork::Texture texture) { glDeleteTextures(1,&texture.ID); //stbi_image_free(texture.data); //texture.data = NULL; }
Genrate_Dungeon.cpp

cpp

Generate_Dungeon::Generate_Dungeon() { area.resize(0); area.push_back(Area { 100 * 100,glm::ivec2(0,0),glm::ivec2(100,100) }); } /* 文字数の関係で省略 */

良い質問の評価を上げる

以下のような質問は評価を上げましょう

  • 質問内容が明確
  • 自分も答えを知りたい
  • 質問者以外のユーザにも役立つ

評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

気になる質問をクリップする

クリップした質問は、後からいつでもマイページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

  • プログラミングに関係のない質問
  • やってほしいことだけを記載した丸投げの質問
  • 問題・課題が含まれていない質問
  • 意図的に内容が抹消された質問
  • 過去に投稿した質問と同じ内容の質問
  • 広告と受け取られるような投稿

評価を下げると、トップページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

int32_t

2022/05/03 06:53

この質問は参考サイトの何を参考にしたのでしょうか?
itagagaki

2022/05/03 07:01

new Generate_Dungeon() は問題なく実行されますか?
samidare_chan

2022/05/03 07:23 編集

int32_t 様 なんとなく見たサイトです。 itagaki様 コンストラクタは実装されております。提示コードを追加しました。
itagagaki

2022/05/03 07:29

たとえば実験的に Stage::Stage() { Generate_Dungeon* p = new Generate_Dungeon(); if (!p) { // failure } } みたいなテストをしてみましたか?
Zuishin

2022/05/03 07:31 編集

全く関係ないところまでいくらでも質問を追加してきて、最後は無言で削除する質問者。
samidare_chan

2022/05/03 07:31

その処理をコメントアウトして実行しましたがはやり FrameWork::LoadTexture()関数が原因があることが判明しました。
samidare_chan

2022/05/03 07:41

Zuishin 様 すいませんでした。
itagagaki

2022/05/03 08:00

まず、 FrameWork::LoadTexture() を呼ばないことでエラーが出なくなったからといって、必ずしも FrameWork::LoadTexture() が原因だと断定することはできないと思いますよ。 そして私が尋ねた new Generate_Dungeon() はできるかどうかをテストしてみないのはなぜですか? 私がなぜそれをテストするよう勧めたのかというと、スタックトレースを分析すると std::allocate_shared<Generate_Dungeon> の処理の先で問題が起こったように見えるからです。
samidare_chan

2022/05/03 08:09

なるほど。しかし別の場所に問題があったみたいで。原因がわからないのですがいじったら治ってしまいました。この場合質問はどうすればいいのでしょうか?
int32_t

2022/05/03 15:06

> いじったら治ってしまいました。この場合質問はどうすればいいのでしょうか? 質問を削除するのではなく、何をいじったら直ったのかを自己回答しましょう。 itagagaki さんのおっしゃる通り LoadTexture() が原因とは限りませんが、LoadTexture() が原因だとすると FrameWork::Texture がコピーしたらまずい定義をしている可能性があります。

まだ回答がついていません

会員登録して回答してみよう

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
87.20%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問

同じタグがついた質問を見る

OpenGL

OpenGLは、プラットフォームから独立した、デスクトップやワークステーション、モバイルサービスで使用可能な映像処理用のAPIです。

C++

C++はC言語をもとにしてつくられた最もよく使われるマルチパラダイムプログラミング言語の1つです。オブジェクト指向、ジェネリック、命令型など広く対応しており、多目的に使用されています。