【发布时间】:2021-12-29 08:07:30
【问题描述】:
这完全是在黑暗中拍摄的,这可能是在浪费时间,但你永远不会知道。我正在使用 GNAT Studio Community 2021 (Ada2012) 并试图让音频库正常工作。我很清楚有零个专门用 Ada 编写的音频库,所以它当然是 C、C++ 和一些 Ada 示例代码的混合。
到目前为止我做了什么:
包括我需要的所有目录。 勾选“项目属性”下的“语言”框以包括 C 和 C++ 文件的使用以使它们可见。 将所需的 DLL(包含在音频库文件夹中)C/P 到我项目的“src”目录中。
到目前为止,完成上述所有操作后,它确实可以编译,所以我已经完成了一半的工作。但是,我收到大量链接器错误,这些错误似乎是指缺少的函数(它们是 C/C++ 函数,而不是 Ada)。尽管我包括了所有相关文件并使它们可见。
这是编译器的结果(我已经从第一行裁剪了它,因为其余的只是同一目标文件中缺少函数定义的延续)。
*
Compile
[Ada] main.adb
Bind
[gprbind] main.bexch
[Ada] main.ali
Link
[link] main.adb
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe:
libamos.a(oal.o):oal.cpp:(.text+0x10): undefined reference to
`__imp_alcOpenDevice'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe:
libamos.a(oal.o):oal.cpp:(.text+0x4c): undefined reference to
`__imp_alcCreateContext’
这是我为测试是否一切正常而编写的代码。
with al_h;
with alc_h;
with snd;
with snd4ada;
with sndloop;
procedure Main is
begin
null;
end Main;
作为参考,这里是库附带的工作代码。
with text_io; use text_io;
with snd4ada;
with interfaces.c;
with interfaces.c.strings;
with ada.command_line;
procedure one is
-- plays WAV file given on command line
subtype glint is interfaces.c.int;
linestr: string(1..80);
last: natural;
music: glint;
begin
if ada.command_line.argument_count = 1 then
declare
title : string := Ada.Command_Line.Argument(1);
begin --declare
snd4ada.initSnds;
music:=snd4ada.initLoop(
interfaces.c.Strings.New_string(title));
put_line("Hit <enter> to begin");
get_line(linestr,last);
snd4ada.playLoop(music);
put_line("hit <enter> to end");
get_line(linestr,last);
snd4ada.stopLoop(music);
snd4ada.termSnds;
end; --declare
end if;
end one;
我的猜测是问题是由于链接器开关可能我需要在项目设置下切换,因此它可以将 C、C++ 和 Ada 代码绑定在一起。
我只是在这里为失败的事业而战吗?我很想让它工作,似乎我唯一的问题是告诉链接器声明在哪里(即使我已将所有相关文件都包含在项目路径中)。
如果有人可以提供帮助,我会非常高兴。如果我知道如何为 Ada 编写自己的音频库,但似乎第三方是唯一的出路。顺便说一句 - 我确实试图让 BASS 工作,但那是不行的。这个是最接近工作的——这很烦人,因为示例代码生成了一个确实可以工作的 .exe。所以这一定是我对链接器做错了。
编辑
这是我的 GPR 文件的内容。
project Amos is
for Source_Dirs use ("src", "External Libs/adaOal19oct21/adaOpenAL", "External Libs/adaOal19oct21/adaOpenAL/OalBinding", "External Libs/adaOal19oct21/adaOpenAL/OalBinding/incoal");
for Object_Dir use "obj";
for Main use ("main.adb");
for Languages use ("Ada", "C", "C++");
end Amos;
大家好。是的,我仍然想让 Ada Open AL 在 GNAT 2021 社区版上工作。我一直在切换一些没有运气的东西。我的一个朋友是 Ada 开发人员,他说他可以让它在使用 Windows NT 的旧 IDE 上工作?
我不断更改我的 GPR 文件。同样,一切都通过了编译器,但在链接器处失败,因为它找不到目标文件,即使我已经添加了所有开关。这是我当前的 GPR 文件。
project Knightmare is
for Source_Dirs use ("src", "../Libs/adaOpenAL", "../Libs/adaOpenAL/OalBinding", "../Libs/adaOpenAL/OalBinding/incoal");
for Object_Dir use "obj";
for Main use ("main.adb");
for Languages use ("Ada", "C", "C++");
package Linker is
for Switches ("c++") use ("g++", "-c", "-fdump-ada-spec", "-C", "oal.hpp", "-Iincoal");
end Linker;
package Compiler is
for Switches ("c++") use ("g++", "-c", "../OalBinding/oal.cpp", "/-std=c++11", "/-fpermissive",
"/-I..", "/-I../OalBinding", "/-I../OalBinding/incoal");
end Compiler;
end Knightmare;
在“项目属性”下检查的语言是 Ada、C 和 C++。包括所有必需的文件夹(如 GPR 中所示)。这可能是我缺少的“依赖”吗?我已经查看了下面的好心用户和 cmets 中提到的 SH(shell 脚本),但我无法将 Shell 脚本添加到项目中,因为它说我没有编译器来处理它。我今天确实找到了这个文件,但这可能是问题所在。
rm *.o
rm obj/*
g++ -c ../OalBinding/oal.cpp \
-std=c++11 \
-fpermissive \
-I.. \
-I../OalBinding \
-I../OalBinding/incoal
gnatmake $1 \
-D obj \
-I.. -I../OalBinding \
-largs \
-lc++ \
oal.o \
\
-framework CoreAudio \
-framework AudioUnit \
-framework AudioToolBox \
-framework OpenAL \
-pthread
这就是链接器正在寻找的绑定所有内容的东西吗?如果是这样,我如何告诉 Ada/C/C++ 链接器这样做?哦,由于某种原因,开关“-pthread”也无效,这看起来很奇怪。
这是链接器错误的截断输出。
\Source\knightmare.gpr
Bind
[gprbind] main.bexch
[Ada] main.ali
Link
[link] main.adb
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x10): undefined reference to `__imp_alcOpenDevice'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x4c): undefined reference to `__imp_alcCreateContext'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x6c): undefined reference to `__imp_alcMakeContextCurrent'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x88): undefined reference to `__imp_alGetError'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x9d): undefined reference to `__imp_alGenBuffers'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0xa6): undefined reference to `__imp_alGetError'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x113): undefined reference to `__imp_alGetError'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x13c): undefined reference to `__imp_alBufferData'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x145): undefined reference to `__imp_alGetError'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x1a8): undefined reference to `__imp_alGetError'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x1bd): undefined reference to `__imp_alGenSources'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x1c6): undefined reference to `__imp_alGetError'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x22b): undefined reference to `__imp_alGetError'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x245): undefined reference to `__imp_alSourcei'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x24e): undefined reference to `__imp_alGetError'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x2be): undefined reference to `__imp_alDeleteSources'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x2d3): undefined reference to `__imp_alDeleteBuffers'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x2f7): undefined reference to `__imp_alcDestroyContext'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x307): undefined reference to `__imp_alcCloseDevice'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x325): undefined reference to `__imp_alSourceStop'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x343): undefined reference to `__imp_alSourcePlay'
c:/gnat/2021/bin/../libexec/gcc/x86_64-w64-mingw32/10.3.1/ld.exe: libknightmare.a(oal.o):oal.cpp:(.text+0x36d): undefined reference to `__imp_alGetSourcei'
collect2.exe: error: ld returned 1 exit status
gprbuild: link of main.adb failed
gprbuild: failed command was: c:\gnat\2021\bin\g++.exe main.o b__main.o C:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\al_h.o C:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\alc_h.o C:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\enemy.o C:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\oal_hpp.o C:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\player.o C:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\knightmare.o C:\Users\Amynu\OneDrive\Documents\Knig
htmare\Source\obj\snd.o C:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\sndloop.o C:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\snd4ada.o libknightmare.a -LC:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\ -LC:\Users\Amynu\OneDrive\Documents\Knightmare\Source\obj\ -LC:/gnat/2021/lib/gcc/x86_64-w64-mingw32/10.3.1/adalib/ C:/gnat/2021/lib/gcc/x86_64-w64-mingw32/10.3.1/adalib/libgnarl.a C:/gnat/2021/lib/gcc/x86_64-w64-mingw32/10.3.1/adalib/libgnat.a -Xlinker --stack=0x200000
,0x1000 -mthreads -shared-libgcc -o main.exe
[2021-11-24 10:53:20] process exited with status 4, 100% (11/11), elapsed time: 01.42s
Could not execute "debug set line breakpoint"
我知道我快要让它发挥作用了。我什至给 Ada Open Al 的创建者发了电子邮件,但已经三天没有人回复我了。关于如何使其在 GNAT 2021 社区下运行的 youtube 视频为零,而网络上的信息很少且无用。
如果有人能指出一个可能的解决方案,我会永远为此感到高兴。顺便说一句,我知道 Ada 有一个 SDL 绑定,但它只适用于 Win32 机器(它已经很老了),所以它也被排除在外了。
【问题讨论】:
-
你的项目文件可能有问题吗?它与库提供的示例相比如何?
-
嗯。唯一的区别是该示例使用了其他“with”包含。我也试过这个,但我得到了同样的错误。如果有帮助,这就是我的 GPR 文件的样子。
-
如果您正在查看 github.com/fastrgv/Portable-OpenAL-Sound(示例代码在下载中,而不是在 repo 中!不是好的做法),您将看到 Linux 构建
lcmp.sh中的脚本;您的 GPR 需要反映这一点。查看您的示例 GPR,我完全不确定路径中是否有空格 ..External Libs/....。值得一提的是,macOS 构建脚本ocmp.sh惨败 -
是的,我认为这就是问题所在。如何将此文件添加到我当前的 GPR?我不太了解 C 或 C++。难道只是C/P到正确的目录让GPR能找到的情况吗?
-
“macOS 构建脚本
ocmp.sh惨败” - 因为它说的是-lc++而不是-lstdc++。谁知道呢。