Jadi saya telah mendapatkan beberapa pesan nilai misterius yang tidak diinisialisasi dari valgrind dan sudah cukup misteri dari mana nilai buruk itu berasal.
Tampaknya valgrind menunjukkan tempat di mana nilai unitialised akhirnya digunakan, tetapi bukan asal dari nilai yang tidak diinisialisasi.
==11366== Conditional jump or move depends on uninitialised value(s)
==11366== at 0x43CAE4F: __printf_fp (in /lib/tls/i686/cmov/libc-2.7.so)
==11366== by 0x43C6563: vfprintf (in /lib/tls/i686/cmov/libc-2.7.so)
==11366== by 0x43EAC03: vsnprintf (in /lib/tls/i686/cmov/libc-2.7.so)
==11366== by 0x42D475B: (within /usr/lib/libstdc++.so.6.0.9)
==11366== by 0x42E2C9B: std::ostreambuf_iterator<char, std::char_traits<char> > std::num_put<char, std::ostreambuf_iterator<char, std::char_traits<char> > >::_M_insert_float<double>(std::ostreambuf_iterator<char, std::char_traits<char> >, std::ios_base&, char, char, double) const (in /usr/lib/libstdc++.so.6.0.9)
==11366== by 0x42E31B4: std::num_put<char, std::ostreambuf_iterator<char, std::char_traits<char> > >::do_put(std::ostreambuf_iterator<char, std::char_traits<char> >, std::ios_base&, char, double) const (in /usr/lib/libstdc++.so.6.0.9)
==11366== by 0x42EE56F: std::ostream& std::ostream::_M_insert<double>(double) (in /usr/lib/libstdc++.so.6.0.9)
==11366== by 0x81109ED: Snake::SnakeBody::syncBodyPos() (ostream:221)
==11366== by 0x810B9F1: Snake::Snake::update() (snake.cpp:257)
==11366== by 0x81113C1: SnakeApp::updateState() (snakeapp.cpp:224)
==11366== by 0x8120351: RoenGL::updateState() (roengl.cpp:1180)
==11366== by 0x81E87D9: Roensachs::update() (rs.cpp:321)
Seperti yang dapat dilihat, ini menjadi sangat samar .. terutama karena ketika dikatakan oleh Class :: MethodX, kadang-kadang menunjuk langsung ke ostream dll. Mungkin ini karena optimasi?
==11366== by 0x81109ED: Snake::SnakeBody::syncBodyPos() (ostream:221)
Seperti itu. Apakah ada sesuatu yang saya lewatkan? Apa cara terbaik untuk menangkap nilai buruk tanpa harus menggunakan pekerjaan detektif printf yang sangat lama?
Memperbarui:
Saya menemukan apa yang salah, tetapi anehnya, valgrind tidak melaporkannya ketika nilai buruk pertama kali digunakan. Itu digunakan dalam fungsi multiplikasi:
movespeed = stat.speedfactor * speedfac * currentbendfactor.val;
Di mana speedfac adalah pelampung yang disatukan. Namun, pada saat itu tidak dilaporkan dan tidak sampai nilainya dicetak bahwa saya mendapatkan kesalahan .. Apakah ada pengaturan untuk valgrind untuk mengubah perilaku ini?
Ini artinya Anda mencoba mencetak / mengeluarkan nilai yang setidaknya sebagian tidak diinisialisasi. Bisakah Anda mempersempitnya sehingga Anda tahu persis nilai apa itu? Setelah itu, telusuri kode Anda untuk melihat di mana kode itu diinisialisasi. Kemungkinannya adalah, Anda akan melihat bahwa itu tidak sepenuhnya diinisialisasi.
Jika Anda memerlukan bantuan lebih lanjut, memposting bagian kode sumber yang relevan mungkin memungkinkan seseorang menawarkan lebih banyak panduan.
EDIT
Saya melihat Anda telah menemukan masalah. Perhatikan bahwa valgrind mengawasi lompatan kondisional atau bergerak berdasarkan variabel unitial. Artinya adalah bahwa ia hanya akan memberikan peringatan jika eksekusi program diubah karena nilai yang tidak diinisialisasi (mis. Program mengambil cabang yang berbeda dalam pernyataan if, misalnya). Karena aritmatika yang sebenarnya tidak melibatkan lompatan atau gerakan bersyarat, valgrind tidak memperingatkan Anda tentang itu. Alih-alih, ia menyebarkan status "tidak diinisialisasi" ke hasil pernyataan yang menggunakannya.
Ini mungkin tampak berlawanan dengan intuisi bahwa itu tidak memperingatkan Anda dengan segera, tetapi seperti yang ditunjukkan oleh mark4o , itu melakukan ini karena nilai-nilai yang tidak diinisialisasi digunakan dalam C sepanjang waktu (contoh: bantalan dalam struktur,
realloc()
panggilan, dll.) Sehingga peringatan itu tidak akan sangat berguna karena frekuensi positif palsu.sumber