corner imagecorner image
IDEPlatformPluginsDocs & SupportCommunityPartners

在 Solaris 操作系统上使用线程微状态工具 - NetBeans IDE 6.8 教程

目录

本页上的内容适用于 NetBeans IDE 6.8
要求
简介
为教程设置 Solaris 环境
为教程创建项目
设置项目属性
生成和运行性能分析演示项目
了解线程微状态
线程状态定义
另请参见
小结

要求

要学习本教程,您需要具备以下软件。

软件 要求的版本
Solaris 10 或 OpenSolaris 操作系统 OpenSolaris、Solaris 操作系统版本 10
NetBeans IDE(支持 C/C++) 版本 6.8
Java Development Kit (JDK) 版本 6 或版本 5
C 和 C++ 编译器、makegdb 下文中提供了适用于 Solaris 的工具版本:
经测试可以与 NetBeans IDE 配合使用的 C/C++ 工具集合

请参见 NetBeans IDE 6.8 安装说明配置 NetBeans IDE 以使用 C/C++/Fortran
以获取有关下载并安装所需 NetBeans 软件的信息。

简介

具有 C/C++/Fortran 插件的 NetBeans IDE 6.8 包含线程微状态工具,用于观察线程的执行状态。该工具显示项目线程不断变化的运行时状态的总体视图以及各个线程状态的更详细视图。您可以检测在调试代码时可能无法检测的应用程序运行时问题。

本教程说明了如何在 Solaris 10 或 OpenSolaris 操作系统上运行的 C/C++ 项目中使用线程微状态工具。只有 Solaris 操作系统支持该工具,因为需要使用 Solaris 微状态记帐技术和 DTrace 实用程序来收集线程状态数据。在 Solaris 操作系统上运行 NetBeans 项目时,将缺省运行线程微状态工具。

如果在 Linux、Windows 或 MacOS X 客户端上运行 IDE,并且网络上有可用的 Solaris 系统,则可以将项目设置为使用 Solaris 系统作为远程开发主机。通过进行远程开发,即使您在 Linux、Windows 或 MacOS X 上运行 IDE,也可以使用线程微状态性能分析工具和其他基于 Solaris 的工具。有关如何进行设置以在远程开发主机上生成项目的更多信息,请参见 C/C++ 远程开发教程

本教程使用在基于 SPARC 处理器的 Solaris 系统上运行的项目。如果在基于 SPARC 或 x86 的 Solaris 或 OpenSolaris 系统上运行 NetBeans IDE 6.8,则可以按照本教程中的步骤进行操作。请注意,本教程使用“Solaris 操作系统”表示 OpenSolaris 和 Solaris 10 操作系统。

Solaris 微状态记帐

很多操作系统在每个 CPU 时钟周期内或按固定时间间隔收集 CPU 统计信息。Solaris 操作系统使用一项称为“微状态记帐”的技术,针对每个事件收集 CPU 和线程的统计信息。系统跟踪每个线程的活动,并记录每个线程从一种执行状态转变为另一种状态的时间。可以通过这些时间戳,查看线程在运行、休眠、等待和被阻止等状态下花费的时间。该技术可以收集非常精确的统计信息,而不会显著增加系统开销。

有关微状态记帐的更多信息,请参见 Sun 工程师 Eric Schrock 博客以了解有关 Solaris 10 中的微状态记帐的信息。

为教程设置 Solaris 环境

要使用线程微状态工具,运行 NetBeans 时使用的 Solaris 用户帐户必须具有足够的 DTrace 权限才能观察系统行为。用户帐户必须具有 dtrace_user、dtrace_proc 和 dtrace_kernel 权限。

如果要在 Solaris 远程开发主机上运行项目,则必须在远程主机上为您的用户帐户设置 DTrace 权限。

要检查您的 DTrace 权限,请在命令提示符下键入以下命令:
/bin/ppriv $$

如果您的帐户具有所需的权限,ppriv 命令应返回如下内容:

E: basic,dtrace_kernel,dtrace_proc,dtrace_user
I: basic,dtrace_kernel,dtrace_proc,dtrace_user
P: basic,dtrace_kernel,dtrace_proc,dtrace_user
L: all

以 "I:" 开头的行很重要,因为它指定了从 shell 中启动的程序所继承的权限。如果您的帐户没有所需的可继承权限,并且您没有系统的管理员权限或 root 访问权限,应请求系统管理员为您的帐户添加 dtrace_user、dtrace_proc 和 dtrace_kernel 可继承权限。

如果您具有系统的管理员权限或 root 访问权限,则可以为您的用户帐户授予所需的权限,如下所述。

要为用户帐户永久授予所需的 DTrace 权限,请执行以下操作:
  1. 确保已从系统中注销要修改权限的用户帐户。
  2. 以超级用户 (root) 或其他管理员用户的身份登录。
  3. 在命令提示符下键入以下命令,并将 username 替换为要修改的用户帐户名:
    $ usermod -K defaultpriv=basic,dtrace_kernel,dtrace_user,dtrace_proc username
然后,您可以登录到该用户帐户,启动 NetBeans IDE,并使用具有 DTrace 数据提供器的性能分析工具。

要为用户帐户暂时授予所需的 DTrace 权限,请执行以下操作:

  1. 键入以下命令以确定 shell 进程的进程 ID:
    $ echo $$
  2. 成为超级用户 (root) 或其他管理员用户。
  3. 键入以下命令,将 process-ID 替换为从 echo 命令返回的进程 ID:
    $ ppriv -s I+dtrace_user,dtrace_proc,dtrace_kernel process-ID
现在,在 process-ID 指定的 shell 中键入的所有命令将继承所需的权限。用户帐户可以在该 shell 中启动 NetBeans IDE,并使用线程微状态性能分析工具。

为教程创建项目

为了说明线程微状态性能分析功能,我们将通过 IDE 中包含的性能分析演示样例应用程序创建一个新项目。

性能分析演示应用程序包含三个阶段,每个阶段在 10 秒钟内重复执行两个任务,以使用三种不同的方法生成一些相关活动以便在性能分析工具中进行显示。第一个任务在文件中写入一些数据,第二个任务执行一些计算。每个任务集(包含两个任务)的执行次数等于在开发主机上检测到的 CPU 数。对于单处理器系统,该程序执行一次任务集(包含两个任务)。对于具有 32 个内核的开发主机,该程序执行 32 次任务集(包含两个任务)。必须按 Enter 键才能开始执行每个任务集,因此,您必须注意这一情况。

性能分析演示的各个阶段如下所示:

  • 串行演示是一个单线程程序,它依次运行两个任务,每个任务运行 10 秒。在具有大量 CPU 的系统上,这可能需要一些时间,因为将依次执行更多的任务集。
  • 并行演示是一个多线程程序,它在单独线程中同时执行相同的文件写入和计算任务,每个 CPU 执行一次。在多内核计算机上,此阶段比串行演示快得多,因为此阶段执行的任务数与串行演示相同,但这些任务是同时执行的。不过,无法防止线程竞争访问相同的数据,这可能会导致结果不准确。
  • Pthread 互斥演示也是多线程程序,它执行与其他演示阶段相同的写入和计算任务。但是,这些代码使用互斥锁防止多个线程重叠访问某些函数。

创建性能分析演示项目

  1. 选择“文件”>“新建项目”以打开“新建项目”向导。
  2. 在该向导中,选择“样例”类别,然后选择 "C/C++" 子类别。
  3. 选择图中显示的“性能分析演示”样例,然后单击“下一步”。

    通过“性能分析演示”样例创建新项目的屏幕快照
  4. 您可以选择项目的名称和位置。此处,我们使用缺省的 ProfilingDemo_1 作为项目名称,以及使用缺省的 NetBeansProjects 目录作为项目位置。
  5. 单击“完成”退出向导并创建项目。

设置项目属性

  1. 右键单击“项目”标签中的 "ProfilingDemo_1" 项目节点,然后选择“属性”。
  2. 选择“类别”面板中的“生成”节点。
  3. 选择 "SunStudio_12" 作为工具集合,然后单击“应用”。

  4. 选择项目工具集合的屏幕快照


    也可以使用 GNU 工具集合,因为线程微状态工具不依赖 Sun Studio 工具。

  5. 选择“类别”面板中的“运行”节点。对于“控制台类型”,选择“输出窗口”并单击“应用”。这样,就可以在 IDE 的“输出窗口”而不是外部终端窗口中查看程序输出,如本教程中所示。

  6. 选择项目的控制台输出的屏幕快照


  7. 选择“类别”面板中的“配置文件”节点。选择“在运行过程中显示性能分析指示器”。
  8. 对于“性能分析配置”,选择“C/C++ DTrace 扩展”。

  9. 选择项目“配置文件”选项的屏幕快照
  10. 在“项目属性”对话框中单击“确定”。

生成和运行性能分析演示项目

  1. 右键单击性能分析演示项目节点,然后选择“生成”。
  2. “输出”标签将显示生成的结果,如下所示。如果看到有关参数不匹配的警告,您可以将其忽略。

  3. 生成性能分析演示


  4. 右键单击性能分析演示项目节点,然后选择“运行”。
    在运行性能分析演示项目期间出现提示时,按 Enter 键。输出类似于以下屏幕快照。
  5. 串行演示输出
  6. 将打开“运行监视器”标签,以显示线程微状态工具以及在“C/C++ DTrace 扩展”性能分析配置中指定的所有其他工具的动态图形。
    在以下屏幕快照中,将显示所有工具并以红色突出显示线程微状态工具。
  7. 如果要查看所有工具,您可能需要增加“运行监视器”标签的大小,方法是单击并向上拖动“运行监视器”标签的上边框。也可以拖动右侧使其变宽。


  8. 请注意,在输出窗口中,性能分析演示程序将告诉您所执行的操作,这样您就可以将其与 IDE 在工具中以图形表示的数据进行比较。例如,程序会显示其分配了多少内存,并且还会执行计算,然后释放内存。您可以看到该图反映了程序的活动。

了解线程微状态

“运行监视器”窗口中的线程微状态图形显示了程序线程在项目运行期间进入各种执行状态时的概要信息。Solaris 微状态记帐功能使用 DTrace 工具提供每个线程进入和退出十种不同执行状态时的状态详细信息。

线程微状态工具以图形方式显示项目运行期间创建的所有线程的摘要状态信息。仅显示四种状态:休眠、等待、已阻止和运行。这些状态代表了十种可能的微状态的简化或摘要视图,并概要说明了程序中运行的所有线程的状态。例如,在运行状态下花费的时间代表了所有类型的运行状态:在用户模式下运行、在系统调用中运行、在页面错误中运行以及在陷阱中运行。

  1. 下面的屏幕快照是在开始运行程序的串行演示部分时生成的,该阶段将在单个线程中依次运行两个任务。线程进入休眠状态的时刻对应于程序等待您按 Enter 键的时间。


  2. 请注意,“运行监视器”窗口底部有一个滚动条。请单击并左右拖动该条,以便查看所有性能分析工具中的数据,从运行开始直至结束。
  3. 请注意下面屏幕快照中的大约 0:42 秒的位置,线程微状态中显示的线程数突然变为 3 个,因为程序进入了并行演示部分。主线程启动了两个额外的线程以并行运行两个任务,每个任务在各自的线程中运行。可以看到在等待状态(黄色)和休眠状态(蓝色)下花费了很多时间,而在运行状态(绿色)下却没有花费那么多时间。并行演示部分运行期间没有在已阻止状态(橙色)下花费任何时间,因为程序的该部分没有实施任何线程同步策略(如可阻止线程的互斥锁)。


  4. 请注意下面屏幕快照中的大约 0:56 秒位置,在程序运行期间第一次出现以橙色显示的已阻止微状态。这对应于程序进入 PTHREAD 互斥演示部分的时刻,每个线程将在某些时候使用互斥锁防止其他线程造成干扰。只有在获得互斥锁后,才能运行各个线程。如果某个线程拥有互斥锁,当另一个线程尝试访问代码的锁定部分时,将会阻止该线程。使用互斥锁可防止线程进入数据争用状态,此时,每个线程将重叠访问相同的数据。

  5. 单击“线程详细信息”按钮以显示有关线程微状态的详细信息。
    将打开“线程详细信息”标签,以显示程序中运行的所有线程的图形时间线表示形式以及详细的状态信息。


  6. “线程详细信息”显示程序的完整运行时间内各线程的状态转换。让我们大致了解一下该窗口,看您可以在其中执行哪些操作。

  7. 将鼠标指针移动(但不单击)到线程的某个带颜色区域上方,将会出现一个弹出窗口,其中显示在该特定时刻发生的事件的详细信息。详细信息包括获取数据的时间以及此时各种线程状态所花费的时间百分比。将鼠标指针移动到右侧的“摘要”区域上方时,弹出窗口将显示线程完整运行的百分比。
  8. 显示各种线程状态所花费的时间百分比的弹出窗口

  9. 可通过更改一些设置来控制“线程详细信息”窗口中显示的内容:

    • 单击“详细级别”以选择要查看的详细级别。选项包括“基本”、“中级”或“高级”,最简单的视图仅显示四种常见执行状态,而最复杂的视图显示十种微状态。
    • 单击“显示”列表,然后选择要显示的线程类型。“仅限完成的线程”仅显示程序运行期间已终止的线程。“仅限活动线程”仅显示未终止的线程。“所有线程”同时显示活动线程和完成的线程。
    • 单击单个线程,将会注意到该线程突出显示。然后,按 Shift 键并单击另一个线程以选择一定范围的线程。也可以选择多个不相邻的线程,方法是在单击感兴趣的线程之前按 Ctrl 键。在突出显示所需的线程时,右键单击并选择“仅显示选定线程”。可以使用“显示”列表再次查看所有线程。
    • 右键单击某个线程并选择“线程名称”,将缺省线程名称样式 "Thread n" 更改为线程执行的函数名称。
  10. 可通过单击“线程详细信息”窗口左上角的加号 (+) 按钮,放大线程图形以仔细查看图形并获得更多微状态数据。也可以单击减号 (-) 按钮缩小图形以粗略查看图形。“显示完整运行”按钮在“线程详细信息”窗口中显示整个项目运行数据(无需滚动)。再次单击该按钮可返回到线程详细信息的滚动视图。
  11. 在下面的屏幕快照中,我们可以看到放大的“线程详细信息”窗口。“线程 ID”是线程条目函数,并且将“详细级别”设置为“高级”。



  12. 在“线程详细信息”窗口中单击某个位置,将在下面打开新的“线程调用栈”标签以显示栈转储。在栈转储显示中,可以展开栈中的各个节点以查看栈中的调用,或者右键单击顶部节点并选择“全部展开”以查看此时发生的所有调用。

    在下面的屏幕快照中,我们单击了运行结束附近约 1:03 处的 "Thread 5"。


  13. 单击“线程详细信息”时显示的栈转储
  14. 双击某个未灰显的函数以打开调用该函数的源文件,如以下屏幕中的 mutex_threadfunc

  15. 双击栈转储中的函数时打开的源文件
  16. 在“线程详细信息”窗口中,再次单击某个线程。可以使用鼠标或键盘沿线程时间线进行导航。
  17. 在使用鼠标时,右键单击并选择“导航”>“将插入记号移至左侧”,在当前选择的线程中向左移动焦点。也可以选择“导航”>“设置插入记号”,在时间线中设置一个点,这会更新线程调用栈的内容。可通过选择“导航”>“转至栈视图”,将焦点切换到线程调用栈。

  18. 通过右键单击在“线程详细信息”窗口中导航
  19. 要使用快捷键在“线程详细信息”窗口的线程时间线中进行导航,请按以下键:
    • Ctrl+向左方向键和 Ctrl+向右方向键可在线程时间线中向左或向右滚动。
    • Ctrl+向下方向键可在时间线中选择一个点,这会更新该点的线程调用栈。
    • Alt+向下方向键可将焦点放到“线程调用栈”窗口中的输入。
    • 在“线程调用栈”窗口中,可以使用方向键和 Enter 键打开与函数关联的源文件。

线程状态定义

下面介绍在“高级”详细级别显示的 Solaris 线程微状态。

状态 描述
用户运行 进程在用户模式下花费的时间百分比。
系统运行 进程在系统模式下花费的时间百分比。
其他运行 进程处理系统陷阱等所花费的时间百分比。
文本页面错误 进程处理文本页面错误所花费的时间百分比。
数据页面错误 进程处理数据页面错误所花费的时间百分比。
已阻止 进程等待用户锁所花费的时间百分比。
休眠 进程休眠所花费的时间百分比。
等待 进程等待 CPU 所花费的时间百分比。

另请参见

有关在后台编译运行项目的相关数据时使用 DTrace 技术的更多信息,请参见 BigAdmin DTrace 门户

Solaris 操作系统上 C/C++ 项目的 I/O 性能分析中介绍了 I/O 使用情况工具。

C/C++ 性能分析教程中介绍了 CPU 使用情况、线程使用情况和内存使用情况工具。

有关 NetBeans IDE 的其他 C/C++ 教程,请参见 C/C++ 应用程序学习资源

小结

本教程介绍了有关线程微状态性能分析工具的以下内容:

  • 可以使用 Solaris DTrace 实用程序自动收集 Solaris 平台上的线程微状态信息。
  • 可通过使用性能分析配置选择显示的图形性能分析指示器。
  • 只能在“C/C++ DTrace 扩展”性能分析配置或您自己的配置中找到线程微状态工具。
  • 可以在项目属性的“配置文件”类别中进行性能分析设置。
  • 单击“线程详细信息”按钮可显示有关个别线程的详细状态信息。
  • 单击“线程详细信息”标签中的线程可显示在所选位置运行的所有线程的栈转储。
  • 单击线程栈转储中的函数可在编辑器中打开关联的源文件。
  • 如果您可以访问网络上某个运行 Solaris 操作系统的系统,则可以从 Windows 或 Mac 计算机中使用线程微状态工具,方法是将 Solaris 系统设置为用于生成和运行项目的远程开发主机。