Zenn
🏛️

NetBSD6(i386)のgdbをソースからビルドして可能な限り最新版にする

2024/04/09に公開

TL;DR

  • 確認した範囲ではgdb-8.1.1が上限。ただし動作は不安定
  • gdb-8.2以降はビルドは通せるがデバッグ不可
  • gdb-10.1以降はビルドも通らない(カーネル仕様変更の影響)
  • gdb-8.0以降のビルドはC++11が必要となるため、対応するgccをインストール(今回はgcc-7.1.0)

事前準備:NetBSD6.0.1(i386)のQEMU作成

既に作成済みあるいはホストマシンがあればC++11対応のgccインストールまでスキップ。

以下でQEMUではなくWSLでクロスコンパイル環境を簡単に構築できるなどと書かれているがそのようなことはなく、6ではエラー多発でまともに構築できなかったので不採用。

また、pkgsrcという仕組みもあるがこちらもbootstrapの時点でエラーが発生して構築できなかったので、個別にソースを取得してそれぞれでビルドする。

Windows版QEMUのインストール

インストール後、環境変数PathにC:\Program Files\qemuを追加

QEMUイメージ作成

以下記事を参考。

仮想マシンイメージ作成

任意のワークスペース上で以下実行

command
qemu-img create -f qcow2 netbsd.qcow2 40G

40Gの部分は適当に大きいサイズにしておく。使用した分だけ増える。

OSイメージファイル取得

仮想マシンイメージのワークスペースにNetBSD-6.0.1-i386.isoを保存

初回起動コマンド

command
qemu-system-i386 ^
    -m 1024 ^
    -smp sockets=1,cores=4,threads=2 ^
    -hda netbsd.qcow2 ^
    -cdrom NetBSD-6.0.1-i386.iso ^
    -netdev user,id=n1,ipv6=off ^
    -device e1000,netdev=n1 ^
    -monitor telnet::5555,server,nowait ^
    -rtc base=utc

-mはメモリ。
-smpはCPUの設定。これらは環境に合わせて変える。
ipv6=offとしているのは以下を参考。

インストール

インストールウィザード

1番目を選択

1番目を選択

Japaneseを選択

1番目を選択

Yesを選択

エンター

1番目を選択

1番目を選択

Use the entire diskを選択

Yesを選択

1番目を選択

2番目のスワップサイズを適宜変更

一番下を選択

一番下を選択

エンター

Yesを選択

一番下を選択

1番目を選択

ここでインストールが始まるのでしばらく待つ。

エンター

1番目を選択

エンター

エンター

Yesを選択

localhostなど適当に設定

netbsd6など適当に設定

Noを選択

Yesを選択

Yesを選択

2番目を選択

Japanを選択

エンター

4番目を選択

Yesを選択

rootログイン用パスワードを設定

7番目を選択してsshdを有効にする

一番下を選択

エンター

4番目を選択

ブート画面が出たらウィンドウを閉じる

2回目以降の起動

起動コマンド

command
qemu-system-i386 ^
    -m 1024 ^
    -smp sockets=1,cores=4,threads=2 ^
    -hda netbsd.qcow2 ^
    -netdev user,id=n1,ipv6=off,hostfwd=tcp::22222-:22,hostfwd=tcp::33333-:33333 ^
    -device e1000,netdev=n1 ^
    -monitor telnet::5555,server,nowait ^
    -rtc base=utc

SSHポートをホストの22222にフォワーディングする。33333は予備用。
ログインユーザーはroot

SSH設定

/etc/ssh/sshd_configに編集権限を追加してviで編集。操作方法は割愛。

command
chmod +w /etc/ssh/sshd_config
vi /etc/ssh/sshd_config
  • PermitRootLoginのコメントを削除してyesに変更
  • PubkeyAuthenticationのコメントを削除してyesに変更
  • PasswordEmptyAuthenticationのコメントを削除

以下コマンドでsshd再起動

command
/etc/rc.d/sshd restart

以降はSSHでログイン可能。公開鍵認証は任意。

command
ssh root@localhost -p 22222
Password:
Last login: *** *** ** **:**:** ****
NetBSD 6.0.1 (GENERIC)

Welcome to NetBSD!

Terminal type is xterm-256color.
We recommend that you create a non-root account and use su(1) for root access.
netbsd6#

gdbのバージョン確認

gdb --version

GNU gdb (GDB) 7.3.1
Copyright (C) 2011 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.  Type "show copying"
and "show warranty" for details.
This GDB was configured as "i486--netbsdelf".
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.

C++11対応のgccインストール

GNU makeのビルド・インストール

GNUプロジェクトのソースコードをビルドするためにはGNU makeが必要だが、インストールされているmakeBSD makeなのでまずこれをビルド・インストールする。

command
mkdir -p ~/build_ws
cd ~/build_ws
ftp ftp://ftp.gnu.org/gnu/make/
get make-4.4.1.tar.gz
quit
tar zxvf make-4.4.1.tar.gz
mkdir -p make-4.4.1/build
cd make-4.4.1/build
../configure \
    --build=i486--netbsdelf
make -j8
make install

make-jオプションは同時実行ジョブ数。以降のビルドでも環境に合わせて適宜変更する。

バージョンの確認

/usr/local/bin/make --version

GNU Make 4.4.1
Built for i486--netbsdelf
Copyright (C) 1988-2023 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <https://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

補足

/usr/local/binへのPATH~/.profileで優先度が一番後ろ(初期インストール状態で/usr/localがない)なので、ビルドなどするときに使いたい場合はPATHの一番最初に追加するか、~/.profileを変更しておく。

echo $PATH
/sbin:/usr/sbin:/bin:/usr/bin:/usr/pkg/sbin:/usr/pkg/bin:/usr/X11R7/bin:/usr/X11R6/bin:/usr/local/sbin:/usr/local/bin

本手順ではPATHに追加する方法をとる。

GMP・MPFR・MPCのビルド・インストール

gdbオブジェクトを別マシンでも再利用できるよう、静的ライブラリを生成するようにビルドする。

GMP

command
cd ~/build_ws
ftp ftp://ftp.gnu.org/gnu/gmp/
get gmp-6.3.0.tar.gz
quit
tar zxvf gmp-6.3.0.tar.gz
mkdir -p gmp-6.3.0/build
cd gmp-6.3.0/build
export PATH=/usr/local/bin:$PATH
../configure \
    --build=i486--netbsdelf \
    --enable-static
make -j8
make install
ls -l /usr/local/lib/libgmp.a

-rw-r--r--  1 root  wheel  835696 *** ** **:** /usr/local/lib/libgmp.a

以降のexport PATH=/usr/local/bin:$PATHは同じターミナルのシェルで続けていれば不要。

MPFR

command
cd ~/build_ws
ftp ftp://ftp.gnu.org/gnu/mpfr/
get mpfr-4.2.1.tar.gz
quit
tar zxvf mpfr-4.2.1.tar.gz
mkdir -p mpfr-4.2.1/build
cd mpfr-4.2.1/build
export PATH=/usr/local/bin:$PATH
LDFLAGS=-L/usr/local/lib \
CFLAGS=-I/usr/local/include \
CXXFLAGS=-I/usr/local/include \
../configure \
    --build=i486--netbsdelf \
    --enable-static
make -j8
make install
ls -l /usr/local/lib/libmpfr.a

-rw-r--r--  1 root  wheel  898754 *** ** **:** /usr/local/lib/libmpfr.a

MPC

command
cd ~/build_ws
ftp ftp://ftp.gnu.org/gnu/mpc/
get mpc-1.3.1.tar.gz
quit
tar zxvf mpc-1.3.1.tar.gz
mkdir -p mpc-1.3.1/build
cd mpc-1.3.1/build
export PATH=/usr/local/bin:$PATH
LDFLAGS=-L/usr/local/lib \
CFLAGS=-I/usr/local/include \
CXXFLAGS=-I/usr/local/include \
../configure \
    --build=i486--netbsdelf \
    --enable-static
make -j8
make install
ls -l /usr/local/lib/libmpc.a

-rw-r--r--  1 root  wheel  211676 *** ** **:** /usr/local/lib/libmpc.a

gccのビルド・インストール

gcc-4.7.0以上であればC++11に対応しているのでそれでも良いが、せっかくなのでC++17まで対応しているgcc-7.1.0をインストールする。
※C++20対応のgcc-12.1.0はビルドにC++11以上が必要になるので不採用。

command
cd ~/build_ws
ftp ftp://ftp.gnu.org/gnu/gcc/gcc-7.1.0/
get gcc-7.1.0.tar.gz
quit
tar zxvf gcc-7.1.0.tar.gz
mkdir -p gcc-7.1.0/build

ソースコード修正

  • GMPMPFRMPCを静的ライブラリでのリンクに変更
    これらはデフォルトだと共有ライブラリをリンクするようにしており、PATH/usr/local /libを通していないと毎回gccのたびにエラーを吐くので、静的でのリンクにしておく。
    gcc-7.1.0/configure
    @@ -5405,7 +5405,7 @@ _ACEOF
    
    
     # Check for GMP, MPFR and MPC
    -gmplibs="-lmpc -lmpfr -lgmp"
    +gmplibs="/usr/local/lib/libmpc.a /usr/local/lib/libmpfr.a /usr/local/lib/libgmp.a"
     gmpinc=
     have_gmp=no
    
  • 未対応OS、アーキテクチャ判定ビルドエラーの回避
    gcc-7.1.0/libcilkrts/runtime/os-unix.cにおいて、NetBSDである場合にプリプロセッサでUnsupported OSUnsupported architectureエラーにされてしまう箇所があるので回避する。
    gcc-7.1.0/libcilkrts/runtime/os-unix.c
    @@ -73,6 +73,7 @@
     #elif defined __CYGWIN__ || \
           defined __DragonFly__ || \
           defined __FreeBSD__ || \
    +      defined __NetBSD__  || \
           defined __GNU__
     // No additional include files
    
    @@ -397,6 +398,7 @@ COMMON_SYSDEP int __cilkrts_hardware_cpu_count(void)
         defined __CYGWIN__   || \
         defined __DragonFly__  || \
         defined __FreeBSD__  || \
    +    defined __NetBSD__   || \
         (defined(__sun__) && defined(__svr4__))
         return (int)sysconf(_SC_NPROCESSORS_ONLN);
     #elif defined __MIC__
    @@ -426,6 +428,7 @@ COMMON_SYSDEP void __cilkrts_idle(void)
         // silencing workers that are not stealing work.
     #if defined(__ANDROID__)  || \
         defined(__FreeBSD__)  || \
    +    defined(__NetBSD__)   || \
         defined(__VXWORKS__)  || \
         (defined(__sun__) && defined(__svr4__))
         sched_yield();
    @@ -456,6 +459,7 @@ COMMON_SYSDEP void __cilkrts_yield(void)
         defined(__APPLE__)    || \
         defined(__CYGWIN__)   || \
         defined(__FreeBSD__)  || \
    +    defined(__NetBSD__)   || \
         defined(__VXWORKS__)  || \
         (defined(__sun__) && defined(__svr4__))
         // Call sched_yield to yield quantum.  I'm not sure why we
    
    これをしないとビルド時に以下のようなエラーになる。
    ../../../libcilkrts/runtime/os-unix.c:80:5: error: #error "Unsupported OS"
    #   error "Unsupported OS"
       ^~~~~
    ../../../libcilkrts/runtime/os-unix.c: In function '__cilkrts_hardware_cpu_count':
    ../../../libcilkrts/runtime/os-unix.c:419:2: error: #error "Unsupported architecture"
    #error "Unsupported architecture"
    ^~~~~
    ../../../libcilkrts/runtime/os-unix.c: In function '__cilkrts_idle':
    ../../../libcilkrts/runtime/os-unix.c:440:3: error: #error "Unsupported architecture"
    # error "Unsupported architecture"
     ^~~~~
    ../../../libcilkrts/runtime/os-unix.c: In function '__cilkrts_yield':
    ../../../libcilkrts/runtime/os-unix.c:476:3: error: #error "Unsupported architecture"
    # error "Unsupported architecture"
    
    乱暴な判断だが、この中ではFreeBSDがおそらく最も近いOS・アーキテクチャなのでそれと同じ節に入るようにしている。
    __cilkrts_idle()sched_yield()については一応実装はあるのでリンクは通る。動作は保証できない。
command
export PATH=/usr/local/bin:$PATH
LDFLAGS=-L/usr/local/lib \
CFLAGS=-I/usr/local/include \
CXXFLAGS=-I/usr/local/include \
../configure \
    --build=i486--netbsdelf \
    --prefix=/usr/local/gcc-7.1.0 \
    --enable-static \
    --disable-bootstrap \
    --enable-languages=c,c++ \
    --with-gmp=/usr/local \
    --with-mpfr=/usr/local \
    --with-mpc=/usr/local
make -j8
make install
/usr/local/gcc-7.1.0/bin/gcc --version

gcc (GCC) 7.1.0
Copyright (C) 2017 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

gdbのビルド・インストール

command
cd ~/build_ws
ftp ftp://gcc.gnu.org/pub/gdb/releases/
get gdb-8.1.1.tar.gz
quit
tar zxvf gdb-8.1.1.tar.gz
mkdir -p gdb-8.1.1/build

bsd-kvm.cの未定義ブロック削除

gdb/bsd-kvm.cbsd_kvm_proc_cmd()において、p_addrがどこにも宣言されていないためビルドエラーとなる。
カーネルをデバッグするつもりはないので、暫定的にこのブロックは削除してビルドを通すだけにしておく。ただ後述の動作確認で問題があったのでもしかしたらこの部分は正しく対応する必要があるかもしれないが未確認。
ちなみに記事時点最新のgdb-14.2でも放置されているので、おそらくHAVE_STRUCT_LWPが未定義のBSD系でのリリースビルドはもう行われていないのではないかと思われる。

gdb-8.1.1/gdb/bsd-kvm.c
@@ -292,7 +292,8 @@ bsd_kvm_proc_cmd (const char *arg, int fromtty)
   addr = parse_and_eval_address (arg);
 #ifdef HAVE_STRUCT_LWP
   addr += offsetof (struct lwp, l_addr);
-#else
+/* #else */
+#elif 0
   addr += offsetof (struct proc, p_addr);
 #endif

dwarf2read.cstd::log2の未定義対応

std::log2は廃止されてビルドエラーとなるので、math.hlog2で代用する。

gdb-8.1.1/gdb/dwarf2read.c
@@ -84,6 +84,7 @@
 #include <unordered_map>
 #include "selftest.h"
 #include <cmath>
+#include <math.h>
 #include <set>
 #include <forward_list>
 #include "common/pathstuff.h"
@@ -26088,7 +26089,7 @@ public:
     gdb_assert (m_abbrev_table.empty ());
     const size_t name_count = m_name_to_value_set.size ();
     m_bucket_table.resize
-      (std::pow (2, std::ceil (std::log2 (name_count * 4 / 3))));
+      (std::pow (2, std::ceil (log2 (name_count * 4 / 3))));
     m_hash_table.reserve (name_count);
     m_name_table_string_offs.reserve (name_count);
     m_name_table_entry_offs.reserve (name_count);

参考

gcc-7.1.0が入っていないマシンでも動かせるようにするためにstaticライブラリをリンクするようにしている。

command
cd gdb-8.1.1/build
export PATH=/usr/local/gcc-7.1.0/bin:/usr/local/bin:$PATH
export LD_LIBRARY_PATH=/usr/local/gcc-7.1.0/lib/gcc/i486--netbsdelf/7.1.0:/usr/local/gcc-7.1.0/lib:/usr/local/lib
LDFLAGS="-static -L/usr/local/lib" \
CFLAGS=-I/usr/local/include \
CXXFLAGS=-I/usr/local/include \
    ../configure \
    --build=i486--netbsdelf
make -j8
make install

なお、libstdclibgccGMPMPFRのみをstaticリンクしようとしたがlibgccだけはなぜか共有ライブラリとなってしまうので不採用とした。詳細は以下。

詳細

GMP・MPFR・MPCを静的ライブラリでのリンクに変更

gdb-8.1.1/configure
@@ -5374,7 +5374,7 @@ _ACEOF


 # Check for GMP, MPFR and MPC
-gmplibs="-lmpc -lmpfr -lgmp"
+gmplibs="/usr/local/lib/libmpc.a /usr/local/lib/libmpfr.a /usr/local/lib/libgmp.a"
 gmpinc=
 have_gmp=no

詳しくは確認していないが上記部分は正直意味がなさそうで下記gdb/configureの部分で強制的に.soに書き換えてくるようなので、よくわからないチェック処理は全削除して強制的に静的ライブラリをリンクするように変更する。

gdb-8.1.1/gdb/configure
@@ -9683,456 +9683,7 @@ else
   prefix="$acl_save_prefix"
 
 
-# Check whether --with-libmpfr-prefix was given.
-if test "${with_libmpfr_prefix+set}" = set; then :
-  withval=$with_libmpfr_prefix;
-    if test "X$withval" = "Xno"; then
-      use_additional=no
-    else
-      if test "X$withval" = "X"; then
-
-  acl_save_prefix="$prefix"
-  prefix="$acl_final_prefix"
-  acl_save_exec_prefix="$exec_prefix"
-  exec_prefix="$acl_final_exec_prefix"
-
-          eval additional_includedir=\"$includedir\"
-          eval additional_libdir=\"$libdir\"
-
-  exec_prefix="$acl_save_exec_prefix"
-  prefix="$acl_save_prefix"
-
-      else
-        additional_includedir="$withval/include"
-        additional_libdir="$withval/lib"
-      fi
-    fi
-
-fi
-
-      LIBMPFR=
-  LTLIBMPFR=
-  INCMPFR=
-  rpathdirs=
-  ltrpathdirs=
-  names_already_handled=
-  names_next_round='mpfr '
-  while test -n "$names_next_round"; do
-    names_this_round="$names_next_round"
-    names_next_round=
-    for name in $names_this_round; do
-      already_handled=
-      for n in $names_already_handled; do
-        if test "$n" = "$name"; then
-          already_handled=yes
-          break
-        fi
-      done
-      if test -z "$already_handled"; then
-        names_already_handled="$names_already_handled $name"
-                        uppername=`echo "$name" | sed -e 'y|abcdefghijklmnopqrstuvwxyz./-|ABCDEFGHIJKLMNOPQRSTUVWXYZ___|'`
-        eval value=\"\$HAVE_LIB$uppername\"
-        if test -n "$value"; then
-          if test "$value" = yes; then
-            eval value=\"\$LIB$uppername\"
-            test -z "$value" || LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$value"
-            eval value=\"\$LTLIB$uppername\"
-            test -z "$value" || LTLIBMPFR="${LTLIBMPFR}${LTLIBMPFR:+ }$value"
-          else
-                                    :
-          fi
-        else
-                              found_dir=
-          found_la=
-          found_so=
-          found_a=
-          if test $use_additional = yes; then
-            if test -n "$shlibext" && test -f "$additional_libdir/lib$name.$shlibext"; then
-              found_dir="$additional_libdir"
-              found_so="$additional_libdir/lib$name.$shlibext"
-              if test -f "$additional_libdir/lib$name.la"; then
-                found_la="$additional_libdir/lib$name.la"
-              fi
-            else
-              if test -f "$additional_libdir/lib$name.$libext"; then
-                found_dir="$additional_libdir"
-                found_a="$additional_libdir/lib$name.$libext"
-                if test -f "$additional_libdir/lib$name.la"; then
-                  found_la="$additional_libdir/lib$name.la"
-                fi
-              fi
-            fi
-          fi
-          if test "X$found_dir" = "X"; then
-            for x in $LDFLAGS $LTLIBMPFR; do
-
-  acl_save_prefix="$prefix"
-  prefix="$acl_final_prefix"
-  acl_save_exec_prefix="$exec_prefix"
-  exec_prefix="$acl_final_exec_prefix"
-  eval x=\"$x\"
-  exec_prefix="$acl_save_exec_prefix"
-  prefix="$acl_save_prefix"
-
-              case "$x" in
-                -L*)
-                  dir=`echo "X$x" | sed -e 's/^X-L//'`
-                  if test -n "$shlibext" && test -f "$dir/lib$name.$shlibext"; then
-                    found_dir="$dir"
-                    found_so="$dir/lib$name.$shlibext"
-                    if test -f "$dir/lib$name.la"; then
-                      found_la="$dir/lib$name.la"
-                    fi
-                  else
-                    if test -f "$dir/lib$name.$libext"; then
-                      found_dir="$dir"
-                      found_a="$dir/lib$name.$libext"
-                      if test -f "$dir/lib$name.la"; then
-                        found_la="$dir/lib$name.la"
-                      fi
-                    fi
-                  fi
-                  ;;
-              esac
-              if test "X$found_dir" != "X"; then
-                break
-              fi
-            done
-          fi
-          if test "X$found_dir" != "X"; then
-                        LTLIBMPFR="${LTLIBMPFR}${LTLIBMPFR:+ }-L$found_dir -l$name"
-            if test "X$found_so" != "X"; then
-                                                        if test "$enable_rpath" = no || test "X$found_dir" = "X/usr/lib"; then
-                                LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$found_so"
-              else
-                                                                                haveit=
-                for x in $ltrpathdirs; do
-                  if test "X$x" = "X$found_dir"; then
-                    haveit=yes
-                    break
-                  fi
-                done
-                if test -z "$haveit"; then
-                  ltrpathdirs="$ltrpathdirs $found_dir"
-                fi
-                                if test "$hardcode_direct" = yes; then
-                                                      LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$found_so"
-                else
-                  if test -n "$hardcode_libdir_flag_spec" && test "$hardcode_minus_L" = no; then
-                                                            LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$found_so"
-                                                            haveit=
-                    for x in $rpathdirs; do
-                      if test "X$x" = "X$found_dir"; then
-                        haveit=yes
-                        break
-                      fi
-                    done
-                    if test -z "$haveit"; then
-                      rpathdirs="$rpathdirs $found_dir"
-                    fi
-                  else
-                                                                                haveit=
-                    for x in $LDFLAGS $LIBMPFR; do
-
-  acl_save_prefix="$prefix"
-  prefix="$acl_final_prefix"
-  acl_save_exec_prefix="$exec_prefix"
-  exec_prefix="$acl_final_exec_prefix"
-  eval x=\"$x\"
-  exec_prefix="$acl_save_exec_prefix"
-  prefix="$acl_save_prefix"
-
-                      if test "X$x" = "X-L$found_dir"; then
-                        haveit=yes
-                        break
-                      fi
-                    done
-                    if test -z "$haveit"; then
-                      LIBMPFR="${LIBMPFR}${LIBMPFR:+ }-L$found_dir"
-                    fi
-                    if test "$hardcode_minus_L" != no; then
-                                                                                        LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$found_so"
-                    else
-                                                                                                                                                                                LIBMPFR="${LIBMPFR}${LIBMPFR:+ }-l$name"
-                    fi
-                  fi
-                fi
-              fi
-            else
-              if test "X$found_a" != "X"; then
-                                LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$found_a"
-              else
-                                                LIBMPFR="${LIBMPFR}${LIBMPFR:+ }-L$found_dir -l$name"
-              fi
-            fi
-                        additional_includedir=
-            case "$found_dir" in
-              */lib | */lib/)
-                basedir=`echo "X$found_dir" | sed -e 's,^X,,' -e 's,/lib/*$,,'`
-                additional_includedir="$basedir/include"
-                ;;
-            esac
-            if test "X$additional_includedir" != "X"; then
-                                                                                                                if test "X$additional_includedir" != "X/usr/include"; then
-                haveit=
-                if test "X$additional_includedir" = "X/usr/local/include"; then
-                  if test -n "$GCC"; then
-                    case $host_os in
-                      linux*) haveit=yes;;
-                    esac
-                  fi
-                fi
-                if test -z "$haveit"; then
-                  for x in $CPPFLAGS $INCMPFR; do
-
-  acl_save_prefix="$prefix"
-  prefix="$acl_final_prefix"
-  acl_save_exec_prefix="$exec_prefix"
-  exec_prefix="$acl_final_exec_prefix"
-  eval x=\"$x\"
-  exec_prefix="$acl_save_exec_prefix"
-  prefix="$acl_save_prefix"
-
-                    if test "X$x" = "X-I$additional_includedir"; then
-                      haveit=yes
-                      break
-                    fi
-                  done
-                  if test -z "$haveit"; then
-                    if test -d "$additional_includedir"; then
-                                            INCMPFR="${INCMPFR}${INCMPFR:+ }-I$additional_includedir"
-                    fi
-                  fi
-                fi
-              fi
-            fi
-                        if test -n "$found_la"; then
-                                                        save_libdir="$libdir"
-              case "$found_la" in
-                */* | *\\*) . "$found_la" ;;
-                *) . "./$found_la" ;;
-              esac
-              libdir="$save_libdir"
-                            for dep in $dependency_libs; do
-                case "$dep" in
-                  -L*)
-                    additional_libdir=`echo "X$dep" | sed -e 's/^X-L//'`
-                                                                                                                                                                if test "X$additional_libdir" != "X/usr/lib"; then
-                      haveit=
-                      if test "X$additional_libdir" = "X/usr/local/lib"; then
-                        if test -n "$GCC"; then
-                          case $host_os in
-                            linux*) haveit=yes;;
-                          esac
-                        fi
-                      fi
-                      if test -z "$haveit"; then
-                        haveit=
-                        for x in $LDFLAGS $LIBMPFR; do
-
-  acl_save_prefix="$prefix"
-  prefix="$acl_final_prefix"
-  acl_save_exec_prefix="$exec_prefix"
-  exec_prefix="$acl_final_exec_prefix"
-  eval x=\"$x\"
-  exec_prefix="$acl_save_exec_prefix"
-  prefix="$acl_save_prefix"
-
-                          if test "X$x" = "X-L$additional_libdir"; then
-                            haveit=yes
-                            break
-                          fi
-                        done
-                        if test -z "$haveit"; then
-                          if test -d "$additional_libdir"; then
-                                                        LIBMPFR="${LIBMPFR}${LIBMPFR:+ }-L$additional_libdir"
-                          fi
-                        fi
-                        haveit=
-                        for x in $LDFLAGS $LTLIBMPFR; do
-
-  acl_save_prefix="$prefix"
-  prefix="$acl_final_prefix"
-  acl_save_exec_prefix="$exec_prefix"
-  exec_prefix="$acl_final_exec_prefix"
-  eval x=\"$x\"
-  exec_prefix="$acl_save_exec_prefix"
-  prefix="$acl_save_prefix"
-
-                          if test "X$x" = "X-L$additional_libdir"; then
-                            haveit=yes
-                            break
-                          fi
-                        done
-                        if test -z "$haveit"; then
-                          if test -d "$additional_libdir"; then
-                                                        LTLIBMPFR="${LTLIBMPFR}${LTLIBMPFR:+ }-L$additional_libdir"
-                          fi
-                        fi
-                      fi
-                    fi
-                    ;;
-                  -R*)
-                    dir=`echo "X$dep" | sed -e 's/^X-R//'`
-                    if test "$enable_rpath" != no; then
-                                                                  haveit=
-                      for x in $rpathdirs; do
-                        if test "X$x" = "X$dir"; then
-                          haveit=yes
-                          break
-                        fi
-                      done
-                      if test -z "$haveit"; then
-                        rpathdirs="$rpathdirs $dir"
-                      fi
-                                                                  haveit=
-                      for x in $ltrpathdirs; do
-                        if test "X$x" = "X$dir"; then
-                          haveit=yes
-                          break
-                        fi
-                      done
-                      if test -z "$haveit"; then
-                        ltrpathdirs="$ltrpathdirs $dir"
-                      fi
-                    fi
-                    ;;
-                  -l*)
-                                        names_next_round="$names_next_round "`echo "X$dep" | sed -e 's/^X-l//'`
-                    ;;
-                  *.la)
-                                                                                names_next_round="$names_next_round "`echo "X$dep" | sed -e 's,^X.*/,,' -e 's,^lib,,' -e 's,\.la$,,'`
-                    ;;
-                  *)
-                                        LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$dep"
-                    LTLIBMPFR="${LTLIBMPFR}${LTLIBMPFR:+ }$dep"
-                    ;;
-                esac
-              done
-            fi
-          else
-                                                            LIBMPFR="${LIBMPFR}${LIBMPFR:+ }-l$name"
-            LTLIBMPFR="${LTLIBMPFR}${LTLIBMPFR:+ }-l$name"
-          fi
-        fi
-      fi
-    done
-  done
-  if test "X$rpathdirs" != "X"; then
-    if test -n "$hardcode_libdir_separator"; then
-                        alldirs=
-      for found_dir in $rpathdirs; do
-        alldirs="${alldirs}${alldirs:+$hardcode_libdir_separator}$found_dir"
-      done
-            acl_save_libdir="$libdir"
-      libdir="$alldirs"
-      eval flag=\"$hardcode_libdir_flag_spec\"
-      libdir="$acl_save_libdir"
-      LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$flag"
-    else
-            for found_dir in $rpathdirs; do
-        acl_save_libdir="$libdir"
-        libdir="$found_dir"
-        eval flag=\"$hardcode_libdir_flag_spec\"
-        libdir="$acl_save_libdir"
-        LIBMPFR="${LIBMPFR}${LIBMPFR:+ }$flag"
-      done
-    fi
-  fi
-  if test "X$ltrpathdirs" != "X"; then
-            for found_dir in $ltrpathdirs; do
-      LTLIBMPFR="${LTLIBMPFR}${LTLIBMPFR:+ }-R$found_dir"
-    done
-  fi
-
-
-        ac_save_CPPFLAGS="$CPPFLAGS"
-
-  for element in $INCMPFR; do
-    haveit=
-    for x in $CPPFLAGS; do
-
-  acl_save_prefix="$prefix"
-  prefix="$acl_final_prefix"
-  acl_save_exec_prefix="$exec_prefix"
-  exec_prefix="$acl_final_exec_prefix"
-  eval x=\"$x\"
-  exec_prefix="$acl_save_exec_prefix"
-  prefix="$acl_save_prefix"
-
-      if test "X$x" = "X$element"; then
-        haveit=yes
-        break
-      fi
-    done
-    if test -z "$haveit"; then
-      CPPFLAGS="${CPPFLAGS}${CPPFLAGS:+ }$element"
-    fi
-  done
-
-
-  { $as_echo "$as_me:${as_lineno-$LINENO}: checking for libmpfr" >&5
-$as_echo_n "checking for libmpfr... " >&6; }
-if test "${ac_cv_libmpfr+set}" = set; then :
-  $as_echo_n "(cached) " >&6
-else
-
-    ac_save_LIBS="$LIBS"
-    LIBS="$LIBS $LIBMPFR"
-    cat confdefs.h - <<_ACEOF >conftest.$ac_ext
-/* end confdefs.h.  */
-#include <mpfr.h>
-int
-main ()
-{
-mpfr_exp_t exp; mpfr_t x;
-			 mpfr_frexp (&exp, x, x, MPFR_RNDN);
-  ;
-  return 0;
-}
-_ACEOF
-if ac_fn_c_try_link "$LINENO"; then :
-  ac_cv_libmpfr=yes
-else
-  ac_cv_libmpfr=no
-fi
-rm -f core conftest.err conftest.$ac_objext \
-    conftest$ac_exeext conftest.$ac_ext
-    LIBS="$ac_save_LIBS"
-
-fi
-{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_libmpfr" >&5
-$as_echo "$ac_cv_libmpfr" >&6; }
-  if test "$ac_cv_libmpfr" = yes; then
-    HAVE_LIBMPFR=yes
-
-$as_echo "#define HAVE_LIBMPFR 1" >>confdefs.h
-
-    { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to link with libmpfr" >&5
-$as_echo_n "checking how to link with libmpfr... " >&6; }
-    { $as_echo "$as_me:${as_lineno-$LINENO}: result: $LIBMPFR" >&5
-$as_echo "$LIBMPFR" >&6; }
-  else
-    HAVE_LIBMPFR=no
-            CPPFLAGS="$ac_save_CPPFLAGS"
-    LIBMPFR=
-    LTLIBMPFR=
-  fi
-
-
-
-
-
-
-  if test "$HAVE_LIBMPFR" != yes; then
-    if test "$with_mpfr" = yes; then
-      as_fn_error "MPFR is missing or unusable" "$LINENO" 5
-    else
-      { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: MPFR is missing or unusable; some features may be unavailable." >&5
-$as_echo "$as_me: WARNING: MPFR is missing or unusable; some features may be unavailable." >&2;}
-    fi
-  fi
-fi
+LIBMPFR="/usr/local/lib/libmpfr.a /usr/local/lib/libgmp.a"
 
 # --------------------- #
 # Check for libpython.  #
command
LDFLAGS=-L/usr/local/lib \
CFLAGS=-I/usr/local/include \
CXXFLAGS=-I/usr/local/include \
    ../configure \
    --build=i486--netbsdelf \
    --with-static-standard-libraries
make -j8
make install

lddでみるとなぜかlibgccだけ共有ライブラリを参照してしまっているように見える。

ldd /usr/local/bin/gdb

/usr/local/bin/gdb:
        -lcurses.7 => /usr/lib/libcurses.so.7
        -lterminfo.1 => /usr/lib/libterminfo.so.1
        -lgcc_s.1 => /usr/local/gcc-7.1.0/lib/libgcc_s.so.1
        -lc.12 => /usr/lib/libc.so.12
        -lexpat.2 => /usr/lib/libexpat.so.2
        -llzma.1 => /usr/lib/liblzma.so.1
        -lkvm.6 => /usr/lib/libkvm.so.6
        -lm.0 => /usr/lib/libm.so.0

readelfでみると参照していないようなので、よくわからない。

readelf -d /usr/local/bin/gdb

Dynamic section at offset 0x73cb78 contains 23 entries:
  Tag        Type                         Name/Value
 0x00000001 (NEEDED)                     Shared library: [libcurses.so.7]
 0x00000001 (NEEDED)                     Shared library: [libexpat.so.2]
 0x00000001 (NEEDED)                     Shared library: [liblzma.so.1]
 0x00000001 (NEEDED)                     Shared library: [libkvm.so.6]
 0x00000001 (NEEDED)                     Shared library: [libm.so.0]
 0x00000001 (NEEDED)                     Shared library: [libc.so.12]
 0x00000001 (NEEDED)                     Shared library: [libterminfo.so.1]
 0x0000000c (INIT)                       0x804c530
・・・

gdbのバージョン確認

前述の通り/usr/local/binのPATH優先度はデフォルトでは最後なので、ビルドのシェルを抜けるとプリインストールされているgdbを実行してしまう。優先度を変えても良いが絶対パスで実行する。

/usr/local/bin/gdb --version

GNU gdb (GDB) 8.1.1
Copyright (C) 2018 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.  Type "show copying"
and "show warranty" for details.
This GDB was configured as "i486--netbsdelf".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
<http://www.gnu.org/software/gdb/documentation/>.
For help, type "help".
Type "apropos word" to search for commands related to "word".
ldd /usr/local/bin/gdb

ldd: /usr/local/bin/gdb: not dynamically linked
readelf -d /usr/local/bin/gdb

There is no dynamic section in this file.

共有ライブラリのリンクがないことを確認。

gdb-8.1.1でのデバッグ確認

サンプルコード

sample.c
#include <stdio.h>
#include <unistd.h>

int main(void) {
    int target_value = 10;
    int current_value = 0;

    while (current_value != target_value) {
    	printf("Current value is not the same target value. target: %d current: %d\n", target_value, current_value);
        sleep(5);
    }

    printf("Program end.\n");

    return 0;
}

デバッガでcurrent_value10に書き換えたりしない限り無限ループする。

command
gcc -O0 -g ./sample.c -o sample
./sample

起動済みプロセスにアタッチする形でデバッガを起動

command
/usr/local/bin/gdb \
    --pid $(ps | grep ./sample | grep -v grep | awk '{print $1}')
GNU gdb (GDB) 8.1.1
Copyright (C) 2018 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.  Type "show copying"
and "show warranty" for details.
This GDB was configured as "i486--netbsdelf".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
<http://www.gnu.org/software/gdb/documentation/>.
For help, type "help".
Type "apropos word" to search for commands related to "word".
Attaching to process 12221
Reading symbols from /root/sample/sample...done.
Reading symbols from /usr/local/gcc-7.1.0/lib/libgcc_s.so.1...done.
Reading symbols from /usr/lib/libc.so.12...(no debugging symbols found)...done.
Reading symbols from /usr/libexec/ld.elf_so...(no debugging symbols found)...done.
0xbbade2c7 in _sys___nanosleep50 () from /usr/lib/libc.so.12
(gdb)

適当にブレークポイントを設定して続行

(gdb) b sample.c:10
Breakpoint 1 at 0x8048827: file sample.c, line 10.
(gdb) c
Continuing.

値を書き換えて続行

Breakpoint 1, main () at sample.c:10
10              sleep(5);
(gdb) p current_value=10
$1 = 10
(gdb) c
Continuing.
[Inferior 1 (process 12221) exited normally]
(gdb)

プログラム側の標準出力

Current value is not the same target value. target: 10 current: 0
Current value is not the same target value. target: 10 current: 0
Program end.

アタッチ・デタッチを繰り返すと動作はかなり怪しくなる。

(gdb) detach
Detaching from program: /root/sample/sample, process 7812
(gdb) attach 7812
Attaching to program: /root/sample/sample, process 7812
Reading symbols from /usr/local/gcc-7.1.0/lib/libgcc_s.so.1...done.
Reading symbols from /usr/lib/libc.so.12...(no debugging symbols found)...done.
Reading symbols from /usr/libexec/ld.elf_so...(no debugging symbols found)...done.
0xbbade2c7 in _sys___nanosleep50 () from /usr/lib/libc.so.12
(gdb) b sample.c:10
Breakpoint 1 at 0x8048827: file sample.c, line 10.
(gdb) c
Continuing.

Breakpoint 1, main () at sample.c:10
10              sleep(5);
(gdb) ^CQuit
(gdb) detach
Detaching from program: /root/sample/sample, process 7812
(gdb) attach 7812
Attaching to program: /root/sample/sample, process 7812
Reading symbols from /usr/local/gcc-7.1.0/lib/libgcc_s.so.1...done.
Reading symbols from /usr/lib/libc.so.12...(no debugging symbols found)...done.
Reading symbols from /usr/libexec/ld.elf_so...(no debugging symbols found)...done.
main () at sample.c:10
10              sleep(5);
(gdb) c
Continuing.

Breakpoint 1, main () at sample.c:10
10              sleep(5);
(gdb) c
Continuing.
^C
Program received signal SIGINT, Interrupt.
0xbbade2c7 in _sys___nanosleep50 () from /usr/lib/libc.so.12
(gdb) detach
Detaching from program: /root/sample/sample, process 7812
(gdb) attach 7812
Attaching to program: /root/sample/sample, process 7812
Reading symbols from /usr/local/gcc-7.1.0/lib/libgcc_s.so.1...done.
Reading symbols from /usr/lib/libc.so.12...(no debugging symbols found)...done.
Reading symbols from /usr/libexec/ld.elf_so...(no debugging symbols found)...done.

Program stopped.
0xbbade2c7 in _sys___nanosleep50 () from /usr/lib/libc.so.12
(gdb) c
Continuing.

Breakpoint 1, main () at sample.c:10
10              sleep(5);
(gdb) p current_value=3
$1 = 3
(gdb) c
Continuing.

プログラムは動いているにもかかわらずProgram stopped.と出ているし、そのあと続行してブレークポイントに止まって書き換えもできる。

Current value is not the same target value. target: 10 current: 0
Current value is not the same target value. target: 10 current: 3

おそらくデタッチ時の処理に何らかの問題があると思われる。
また、起動後にattachするとエラーログが出る。

/usr/local/bin/gdb

GNU gdb (GDB) 8.1.1
Copyright (C) 2018 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.  Type "show copying"
and "show warranty" for details.
This GDB was configured as "i486--netbsdelf".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
<http://www.gnu.org/software/gdb/documentation/>.
For help, type "help".
Type "apropos word" to search for commands related to "word".
(gdb) attach 17997
Attaching to process 17997
stat 4 flag 1
Couldn't get registers: Device busy.
(gdb) Reading symbols from /root/sample/sample...done.
Reading symbols from /usr/lib/libgcc_s.so.1...(no debugging symbols found)...done.
Reading symbols from /usr/lib/libc.so.12...(no debugging symbols found)...done.
Reading symbols from /usr/libexec/ld.elf_so...(no debugging symbols found)...done.
0xbbaef2c7 in _sys___nanosleep50 () from /usr/lib/libc.so.12

引数によるプロセスID指定での起動時には出なかったCouldn't get registers: Device busy.というログが出るようになる。

余談

gdb-8.0でのリンク失敗

同一定義名が重複している模様。詳細未確認。

/usr/local/gcc-7.1.0/lib/gcc/i486--netbsdelf/7.1.0/../../../libstdc++.a(math_stubs_long_double.o): In function `frexpl':
/root/gcc/gcc-7.1.0/build/i486--netbsdelf/libstdc++-v3/src/c++98/../../../../../libstdc++-v3/src/c++98/math_stubs_long_double.cc:124: multiple definition of `frexpl'
build-gnulib/import/libgnu.a(frexpl.o):frexpl.c:(.text+0x0): first defined here
collect2: error: ld returned 1 exit status
make[2]: *** [Makefile:2211: gdb] Error 1
make[2]: Leaving directory '/build_ws/gdb-8.0/build/gdb'
make[1]: *** [Makefile:9126: all-gdb] Error 2
make[1]: Leaving directory '/build_ws/gdb-8.0/build'
make: *** [Makefile:849: all] Error 2

gdb-8.2でのデバッグ失敗

ビルドは通るものの、デバッグを始めるとセグ落ちする。coreファイルは吐いてくれるので解析はできると思うが未確認。

./gdb \
    --pid $(ps | grep ./sample | grep -v grep | awk '{print $1}')

GNU gdb (GDB) 8.2
Copyright (C) 2018 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
Type "show copying" and "show warranty" for details.
This GDB was configured as "i486--netbsdelf".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
    <http://www.gnu.org/software/gdb/documentation/>.

For help, type "help".
Type "apropos word" to search for commands related to "word"...
^: No such file or directory.
Attaching to process 4603
Reading symbols from /root/sample/sample...done.
Reading symbols from /usr/lib/libc.so.12...(no debugging symbols found)...done.
Reading symbols from /usr/libexec/ld.elf_so...(no debugging symbols found)...done.
0xbbafb2c7 in _sys___nanosleep50 () from /usr/lib/libc.so.12
(gdb) b sample.c:10
Breakpoint 1 at 0x80487a8: file sample.c, line 10.
(gdb) c
Continuing.
sorry, pid 4603 was killed: orphaned traced process
[1]   Segmentation fault (core dumped) ./gdb ^ --pid $(...)

gdb-10.2でのビルド失敗

カーネルの仕様変更で例えばKERN_PROC_PATHNAMEの定義がなくビルドに失敗する。

../../gdb/nat/netbsd-nat.c: In function 'const char* netbsd_nat::pid_to_exec_file(__pid_t)':
../../gdb/nat/netbsd-nat.c:41:48: error: 'KERN_PROC_PATHNAME' was not declared in this scope
   int mib[4] = {CTL_KERN, KERN_PROC_ARGS, pid, KERN_PROC_PATHNAME};
                                                ^~~~~~~~~~~~~~~~~~
../../gdb/nat/netbsd-nat.c:41:48: note: suggested alternative: 'KERN_PROC_PID'
   int mib[4] = {CTL_KERN, KERN_PROC_ARGS, pid, KERN_PROC_PATHNAME};
                                                ^~~~~~~~~~~~~~~~~~
                                                KERN_PROC_PID
../../gdb/nat/netbsd-nat.c: In function 'void netbsd_nat::enable_proc_events(__pid_t)':
../../gdb/nat/netbsd-nat.c:177:13: error: 'PTRACE_LWP_CREATE' was not declared in this scope
   events |= PTRACE_LWP_CREATE;
             ^~~~~~~~~~~~~~~~~
../../gdb/nat/netbsd-nat.c:177:13: note: suggested alternative: 'PTRACE_TYPE_RET'
   events |= PTRACE_LWP_CREATE;
             ^~~~~~~~~~~~~~~~~
             PTRACE_TYPE_RET
../../gdb/nat/netbsd-nat.c:178:13: error: 'PTRACE_LWP_EXIT' was not declared in this scope
   events |= PTRACE_LWP_EXIT;
             ^~~~~~~~~~~~~~~
../../gdb/nat/netbsd-nat.c:178:13: note: suggested alternative: 'PTRACE_TYPE_RET'
   events |= PTRACE_LWP_EXIT;
             ^~~~~~~~~~~~~~~
             PTRACE_TYPE_RET
../../gdb/nat/netbsd-nat.c: In function 'int netbsd_nat::qxfer_siginfo(__pid_t, const char*, unsigned char*, const unsigned char*, CORE_ADDR, int)':
../../gdb/nat/netbsd-nat.c:190:3: error: 'ptrace_siginfo_t' was not declared in this scope
   ptrace_siginfo_t psi;
   ^~~~~~~~~~~~~~~~
../../gdb/nat/netbsd-nat.c:190:3: note: suggested alternative: 'ptrace_lwpinfo'
   ptrace_siginfo_t psi;
   ^~~~~~~~~~~~~~~~
   ptrace_lwpinfo
../../gdb/nat/netbsd-nat.c:195:15: error: 'PT_GET_SIGINFO' was not declared in this scope
   if (ptrace (PT_GET_SIGINFO, pid, &psi, sizeof (psi)) == -1)
               ^~~~~~~~~~~~~~
../../gdb/nat/netbsd-nat.c:195:15: note: suggested alternative: 'SA_SIGINFO'
   if (ptrace (PT_GET_SIGINFO, pid, &psi, sizeof (psi)) == -1)
               ^~~~~~~~~~~~~~
               SA_SIGINFO
../../gdb/nat/netbsd-nat.c:195:37: error: 'psi' was not declared in this scope
   if (ptrace (PT_GET_SIGINFO, pid, &psi, sizeof (psi)) == -1)
                                     ^~~
../../gdb/nat/netbsd-nat.c:202:37: error: 'psi' was not declared in this scope
     memcpy (readbuf, ((gdb_byte *) &psi.psi_siginfo) + offset, len);
                                     ^~~
../../gdb/nat/netbsd-nat.c:205:30: error: 'psi' was not declared in this scope
       memcpy (((gdb_byte *) &psi.psi_siginfo) + offset, writebuf, len);
                              ^~~
../../gdb/nat/netbsd-nat.c:207:19: error: 'PT_SET_SIGINFO' was not declared in this scope
       if (ptrace (PT_SET_SIGINFO, pid, &psi, sizeof (psi)) == -1)
                   ^~~~~~~~~~~~~~
../../gdb/nat/netbsd-nat.c:207:19: note: suggested alternative: 'SA_SIGINFO'
       if (ptrace (PT_SET_SIGINFO, pid, &psi, sizeof (psi)) == -1)
                   ^~~~~~~~~~~~~~
                   SA_SIGINFO
make[2]: *** [Makefile:1614: nat/netbsd-nat.o] Error 1
make[2]: *** Waiting for unfinished jobs....
../../gdb/nbsd-nat.c: In function 'std::__cxx11::string nbsd_pid_to_cwd(int)':
../../gdb/nbsd-nat.c:50:48: error: 'KERN_PROC_CWD' was not declared in this scope
   int mib[4] = {CTL_KERN, KERN_PROC_ARGS, pid, KERN_PROC_CWD};
                                                ^~~~~~~~~~~~~
../../gdb/nbsd-nat.c:50:48: note: suggested alternative: 'KERN_PROC_PID'
   int mib[4] = {CTL_KERN, KERN_PROC_ARGS, pid, KERN_PROC_CWD};
                                                ^~~~~~~~~~~~~
                                                KERN_PROC_PID
../../gdb/nbsd-nat.c: In function 'gdb::unique_xmalloc_ptr<kinfo_vmentry []> nbsd_kinfo_get_vmmap(__pid_t, size_t*)':
../../gdb/nbsd-nat.c:182:25: error: 'VM_PROC' was not declared in this scope
   int mib[5] = {CTL_VM, VM_PROC, VM_PROC_MAP, pid,
                         ^~~~~~~
../../gdb/nbsd-nat.c:182:25: note: suggested alternative: 'CTL_PROC'
   int mib[5] = {CTL_VM, VM_PROC, VM_PROC_MAP, pid,
                         ^~~~~~~
                         CTL_PROC
../../gdb/nbsd-nat.c:182:34: error: 'VM_PROC_MAP' was not declared in this scope
   int mib[5] = {CTL_VM, VM_PROC, VM_PROC_MAP, pid,
                                  ^~~~~~~~~~~
../../gdb/nbsd-nat.c:182:34: note: suggested alternative: 'VM_PROT_ALL'
   int mib[5] = {CTL_VM, VM_PROC, VM_PROC_MAP, pid,
                                  ^~~~~~~~~~~
                                  VM_PROT_ALL
../../gdb/nbsd-nat.c:183:31: error: invalid application of 'sizeof' to incomplete type 'kinfo_vmentry'
   sizeof (struct kinfo_vmentry)};
                               ^
../../gdb/nbsd-nat.c:206:48: error: invalid application of 'sizeof' to incomplete type 'kinfo_vmentry'
   *size = length / sizeof (struct kinfo_vmentry);
                                                ^
../../gdb/nbsd-nat.c: In member function 'virtual int nbsd_nat_target::find_memory_regions(find_memory_region_ftype, void*)':
../../gdb/nbsd-nat.c:231:16: error: invalid use of incomplete type 'struct kinfo_vmentry'
       if (!(kve->kve_protection & KVME_PROT_READ)
                ^~
../../gdb/nbsd-nat.c:179:39: note: forward declaration of 'struct kinfo_vmentry'
 static gdb::unique_xmalloc_ptr<struct kinfo_vmentry[]>
                                       ^~~~~~~~~~~~~
../../gdb/nbsd-nat.c:231:18: error: invalid use of incomplete type 'struct kinfo_vmentry'
       if (!(kve->kve_protection & KVME_PROT_READ)
                  ^~~~~~~~~~~~~~
../../gdb/nbsd-nat.c:179:39: note: forward declaration of 'struct kinfo_vmentry'
 static gdb::unique_xmalloc_ptr<struct kinfo_vmentry[]>
                                       ^~~~~~~~~~~~~
../../gdb/nbsd-nat.c:231:35: error: 'KVME_PROT_READ' was not declared in this scope
       if (!(kve->kve_protection & KVME_PROT_READ)
                                   ^~~~~~~~~~~~~~
../../gdb/nbsd-nat.c:231:35: note: suggested alternative: 'VM_PROT_READ'
       if (!(kve->kve_protection & KVME_PROT_READ)
                                   ^~~~~~~~~~~~~~
                                   VM_PROT_READ
・・・

NetBSD 8.0にはあるので、これ以降のgdbは新しいバージョンのOSにしか対応していない模様。

6.0.1には定義がない。

gdbserverについて

gdbserverはプリインストールされていない。

gdbserver

gdbserver: not found

gdb-5.2あたりからi386系のNetBSDはビルド対象から外されている。

gdb-5.2/gdb/gdbserver/configure.srv
case "${target}" in
  arm*-*-linux*)	srv_regobj=reg-arm.o
			srv_tgtobj="linux-low.o linux-arm-low.o"
			srv_linux_usrregs=yes
			;;
  i[3456]86-*-linux*)	srv_regobj=reg-i386-linux.o
			srv_tgtobj="linux-low.o linux-i386-low.o i387-fp.o"
			srv_linux_usrregs=yes
			srv_linux_regsets=yes
			;;
  ia64-*-linux*)	srv_regobj=reg-ia64.o

一方でgdb-11.1からはビルド対象となっているが、6でビルドしようとするとgdb-10.2のgdbと同様ビルドエラーとなるので、おそらく新しいバージョンのOSにしか対応していない模様。

gdb-11.1/gdb/gdbserver/configure.srv
  i[34567]86-*-netbsd*)	srv_regobj=""
			srv_tgtobj="netbsd-low.o netbsd-i386-low.o fork-child.o"
			srv_tgtobj="${srv_tgtobj} nat/fork-inferior.o"
			srv_tgtobj="${srv_tgtobj} nat/netbsd-nat.o"
			srv_tgtobj="${srv_tgtobj} arch/i386.o"
			;;
  ia64-*-linux*)	srv_regobj=reg-ia64.o

ただ、この辺りはリリースノートで一切言及されていないので経緯が全く分からない。

どうしてもgdbserverを使いたい場合はgdb-5.2以前のバージョンをビルドするしかない。ただし確認した限りではプロセスのアタッチ起動はできない模様。
あるいは自力でコードを読み解いて実装してみるなど。気を付けることとしてgdbはバージョンによってアーキテクチャがだいぶ異なる場合もあるので、同じ修正を新旧バージョンに必ずしもそのまま反映できるとは限らないことがある。
ちなみに記事時点最新のgdb-14.2では実装されていない。

gdb-14.2/gdbserver/netbsd-low.cc
/* Implement the attach target_ops method.  */

int
netbsd_process_target::attach (unsigned long pid)
{
  /* Unimplemented.  */
  return -1;
}

参考

Discussion

ログインするとコメントできます