——————-Notes for the first debug of pbrt——————-
1.在pbrt-v3下新建一个名为build.debug的文件夹,定位打该文件夹;
cd ~/pbrt-v3/build.debug/
2.用cmake生成debug版本的makefile;
cmake ../ -DCMAKE_BUILD_TYPE=Debug
3.编译生成debug般的可执行文件pbrt;
make -j4
4.链接可执行文件;
sudo ln -s ~/pbrt-v3/build.debug/pbrt /usr/bin/pbrt.debug
5.用gdb开始对pbrt.debug进行debug;开始进入gdb环境;
gdb pbrt.debug
6.在gdb环境中给pbrt.debug设置参数;
set args --nthreads=1 ~/pbrt/killeroos/killeroo-simple.pbrt
7.打开一个新的终端,查找所有实现“Li()”的类;(因为当前不知道会用到什么tracer,所以只有在每个tracer的Li()代码中加断点)
grep -rn "::Li(" ~/pbrt-v3/src/
得到的搜索结果:
/home/lbzeng/pbrt-v3/src/integrators/path.cpp:64:Spectrum PathIntegrator::Li(const RayDifferential &r, const Scene &scene,
/home/lbzeng/pbrt-v3/src/integrators/ao.cpp:57:Spectrum AOIntegrator::Li(const RayDifferential &r, const Scene &scene,
/home/lbzeng/pbrt-v3/src/integrators/volpath.cpp:55:Spectrum VolPathIntegrator::Li(const RayDifferential &r, const Scene &scene,
/home/lbzeng/pbrt-v3/src/integrators/directlighting.cpp:62:Spectrum DirectLightingIntegrator::Li(const RayDifferential &ray,
/home/lbzeng/pbrt-v3/src/integrators/whitted.cpp:44:Spectrum WhittedIntegrator::Li(const RayDifferential &ray, const Scene &scene,
/home/lbzeng/pbrt-v3/src/core/stats.h:199: "SamplerIntegrator::Li()",
8.回到之前的终端,一次设置这些断点(.h文件中不用设置)
b /home/lbzeng/pbrt-v3/src/integrators/path.cpp:65
b /home/lbzeng/pbrt-v3/src/integrators/ao.cpp:58
b /home/lbzeng/pbrt-v3/src/integrators/volpath.cpp:56
b /home/lbzeng/pbrt-v3/src/integrators/directlighting.cpp:63
b /home/lbzeng/pbrt-v3/src/integrators/whitted.cpp:45
可以通过info b查看当前的断点信息
info b
Num Type Disp Enb Address What
1 breakpoint keep y 0x08381a45 in pbrt::PathIntegrator::Li(pbrt::RayDifferential const&, pbrt::Scene const&, pbrt::Sampler&, pbrt::MemoryArena&, int) const at /home/lbzeng/pbrt-v3/src/integrators/path.cpp:65
2 breakpoint keep y 0x08390783 in pbrt::AOIntegrator::Li(pbrt::RayDifferential const&, pbrt::Scene const&, pbrt::Sampler&, pbrt::MemoryArena&, int) const at /home/lbzeng/pbrt-v3/src/integrators/ao.cpp:58
3 breakpoint keep y 0x08391931 in pbrt::VolPathIntegrator::Li(pbrt::RayDifferential const&, pbrt::Scene const&, pbrt::Sampler&, pbrt::MemoryArena&, int) const at /home/lbzeng/pbrt-v3/src/integrators/volpath.cpp:56
4 breakpoint keep y 0x0839700a in pbrt::DirectLightingIntegrator::Li(pbrt::RayDifferential const&, pbrt::Scene const&, pbrt::Sampler&, pbrt::MemoryArena&, int) const at /home/lbzeng/pbrt-v3/src/integrators/directlighting.cpp:63
5 breakpoint keep y 0x08397ebf in pbrt::WhittedIntegrator::Li(pbrt::RayDifferential const&, pbrt::Scene const&, pbrt::Sampler&, pbrt::MemoryArena&, int) const at /home/lbzeng/pbrt-v3/src/integrators/whitted.cpp:45
9.运行(run)
r
然后会在第四个断点处停住:
Thread 1 "pbrt.debug" hit Breakpoint 4, pbrt::DirectLightingIntegrator::Li (
this=0x8a54310, ray=..., scene=..., sampler=..., arena=..., depth=0)
at /home/lbzeng/pbrt-v3/src/integrators/directlighting.cpp:64
64 MemoryArena &arena, int depth) const {
所以,可以确定当前场景用到的积分器(或者说tracer)是directlighting
10.查看断点处的代码;
l 64
然后按几下“回车”(“回车”即“重复上一条指令”)
终端上输出如下信息:
(gdb) l 64
59 }
60 }
61
62 Spectrum DirectLightingIntegrator::Li(const RayDifferential &ray,
63 const Scene &scene, Sampler &sampler,
64 MemoryArena &arena, int depth) const {
65 ProfilePhase p(Prof::SamplerIntegratorLi);
66 Spectrum L(0.f);
67 // Find closest ray intersection or return background radiance
68 SurfaceInteraction isect;
(gdb)
69 if (!scene.Intersect(ray, &isect)) {
70 for (const auto &light : scene.lights) L += light->Le(ray);
71 return L;
72 }
73
74 // Compute scattering functions for surface interaction
75 isect.ComputeScatteringFunctions(ray, arena);
76 if (!isect.bsdf)
77 return Li(isect.SpawnRay(ray.d), scene, sampler, arena, depth);
78 Vector3f wo = isect.wo;
(gdb)
79 // Compute emitted light if ray hit an area light source
80 L += isect.Le(wo);
81 if (scene.lights.size() > 0) {
82 // Compute direct lighting for _DirectLightingIntegrator_ integrator
83 if (strategy == LightStrategy::UniformSampleAll)
84 L += UniformSampleAllLights(isect, scene, arena, sampler,
85 nLightSamples);
86 else
87 L += UniformSampleOneLight(isect, scene, arena, sampler);
88 }
(gdb)
89 if (depth + 1 < maxDepth) {
90 Vector3f wi;
91 // Trace rays for specular reflection and refraction
92 L += SpecularReflect(ray, isect, scene, sampler, arena, depth);
93 L += SpecularTransmit(ray, isect, scene, sampler, arena, depth);
94 }
95 return L;
96 }
97
98 DirectLightingIntegrator *CreateDirectLightingIntegrator(
(gdb)
11.简单看一下代码(这个需要一定的基础,本人之前有学过《Ray Tracing from the Ground Up》)
可以看出最终的颜色值L由四部分组成:漫反射光、光源、高光反射光、折射光。
然后,可以在这些位置分别设置断点:
b 75
b 80
b 84
b 87
b 92
b 93
当程序在某断点处停止时,如果想看看断点处函数的具体实现,可以:
s(进入函数)
n(进入函数后,n指令查看该函数中的下一行代码)
l N(刚进入函数时,对应代码的行数N,指令“l N”显示N行附近的代码,然后,按几次回车,基本可以显示整个函数的代码)
bt(打印出,程序跑至此处的callstack)
12.相关callstack