精华内容
下载资源
问答
  • 逆向分析中常用的分析方法有:静态分析、动态调试、HOOK等。动态调试的好处是:1)可以在调试的过程中知道参数或者局部变量的值以及变化过程,2)可以快速履清代码运行的先后顺序,验证自己的想法是否正确。安卓中...

    安卓逆向之----常用动态调试方法

    一. 前言

    逆向分析中常用的分析方法有:静态分析、动态调试、HOOK等。动态调试的好处是:1)可以在调试的过程中知道参数或者局部变量的值以及变化过程,2)可以快速履清代码运行的先后顺序,验证自己的想法是否正确。安卓中需要调试的代码有dex中代码和so中代码,对于dex层java代码调试,本人常用的是dex Java代码用JEB调试和IDEA + Smalidea调试,so层代码是用IDA附加调试。下面就这三种方法进行一一介绍。

    二. 调试介绍

    命令:adb jdwp 用于查看Android手机中可调式的进程。

    1. JEB调试

    先安装好JEB,并配置好Java环境。JEB调试并不需要事先将apk转换成smali代码,只需要打开和安装到安卓手机上对应的apk文件即可。不过前提是让想要调试的apk支持被调试,这一点对后面的两种调试方法也是要符合才行。至于怎么支持调试?1)apk的Manifest.xml文件的Application的属性中包含android:debuggable=“true” ;2)或者第一条不满足时,安卓手机的default.prop文件中ro.debuggable=1时也行,mprop工具可用于修改该属性值。用JEB调试时,得把Eclipse和Android Studio关掉,不然会占用adb端口。
    做好前期准备后,下面正式进入调试环节:
    (1)打开JEB,并打开一个apk文件,安卓手机打开相应的应用,并且连接好电脑:
    在这里插入图片描述
    在这里插入图片描述
    调试时,需要在smali界面才能单步(可以发现在Java代码界面单步是无效的),但是在调试过程中可以随时切换看源码,单步时切回去即可,调试快捷键直接点击debugger查看,不同版本会有些不同。
    (2)开始附加调试
    点击Debugger——start,然后弹出选择附加进程界面,如下图:
    在这里插入图片描述
    在这里插入图片描述
    (3)查看变量的值
    调试时,变量的值都是地址,即使是String类型也是,所以需要将类型转成String,选中类型,然后Ctrl + 输入String,不过很不稳定,很多时候都不成功,查找变量的值在用smalidea + idea调试时很容易观察。
    在这里插入图片描述
    在这里插入图片描述

    2.smalidea + idea调试

    idea直接到官网下载一个社区版(不收费版,够我们调试用了)安装,然后下载smalidea插件(github地址:https://github.com/JesusFreke/smali/wiki/smalidea
    下载地址:https://bitbucket.org/JesusFreke/smali/downloads),在IDEA界面中选择:File——Setting——Plugin——Install plugin fromdisk…,选择下载好的smalidea插件,安装即可。
    在这里插入图片描述
    环境配好了,接下来介绍调试的步骤:
    (1)找到要调试的应用的相应的apk文件,可以是从手机里面导出来,高版本的系统导出来的apk可能是包含odex文件的,或者是vdex文件的,所以遇到时,得需要将这些文件转成包含dex的apk文件。
    (2)通过apktool工具将apk反编译成smali文件,然后用IDEA打开smali文件所在的总目录。
    在这里插入图片描述
    (3)初次调试时,需要配置:Run——Edit Configurations,点击左上角+,然后选择remote,然后打开DDMS(ddms工具在安装好Android的Eclipse中会自带,也可网上下载),查看需要调试的包名对应的端口,替换掉8700,保存后,Run——debug unnamed,即能实现调试。
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    (4)查看变量的值
    smali+Idea调试时,查看变量很稳定,如下:
    在这里插入图片描述

    3.IDA调试so

    IDA调试so时,可以在打开相应的so文件下调试,也可以在不带so文件的情况下调试,二者都需要附加,常用的是后者,现在直接说明后者的步骤。
    (1)启动IDA的调试服务
    在这里插入图片描述
    根据getprop ro.product.cpu.abi,查看CPU型号,我的是armeabi-v7a,所以选择android_server。

    adb push android_server /data/local/tmp
    adb shell chmod 777 /data/local/tmp/android_server 
    adb shell su
    #:/data/local/tmp/android_server -p3000
    之后另一cmd窗口中映射指定的端口:
    adb forward tcp:3000 tcp:3000
    

    上面最后一行中,5566是给服务指定的端口,默认是23946,也可以改成其它的。必须是root权限下执行这个命令,不然调试进程只会显示两个,不是所有的包名对应的进程。
    (2) 打开IDA开始附加
    IDA一般会有32位和64位,在经验中,64位IDA调试32位的so会出问题,32位的IDA调试64位的so目前没怎么试过,但最好是位数对应好,然后启动相应位数的IDA调试服务。
    选择Debugger——Attach——Remote ARMLinux/Android Debugger;
    在这里插入图片描述
    选择调试的包名
    到这里就可以下断点调试了,如下图,一般会把要调试的so用另一个IDA打开,找到代码偏移,然后加上此时调试时模块的首地址就是我们想调试的地址,下断点,然后F9便可。
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述
    下断点地址:B3D30000 + 7B04 = B3D37B04
    在这里插入图片描述
    有的时候会调试Jni_Onload这个函数,但是这个函数很早就调用了,用上面的步骤是没法调试到这个函数的,这是可以尝试先用JDB调试启动apk,然后用IDA附加,最后用JDB接管调试。JDB是java调试器 ,包含在 SDK 中。 该调试器通过 jdb 命令启动。操作步骤如下:
    (1)在cmd窗口中用:adb shell am start -D -n 包名/Activity名 命令调试启动应用;
    (2)启动IDA的服务,映射端口;
    (3)IDA附加进程;
    (4)jdb -connect com.sun.jdi.SocketAttach:hostname=127.0.0.1,port=8700
    port可以换成ddsm中查看到的相应报名的端口;
    (5)之后在IDA中调试同上面非启动调试一样操作了。

    4. 怎么修改ro.debuggable的值为1

    (1)通过mprop文件修改
    工具下载地址:wpvsyou/mprop
    使用方法:

    getprop ro.product.cpu.abi #获取cpu型号,然后push对应版本的mprop到/data/local/tmp
    adb push mprop /data/local/tmp
    adb shell chmod 777 /data/local/tmp/mprop 
    # 进人adb shell,再如下操作
    /data/local/tmp/mprop ro.debuggable 1
    stop;start # 重启adbd 进程
    

    该方法在手机重启后会失效。之前在nuxus手机中使用时有生效,但在pixel手机中没有生效,目前还不清楚原因。

    (2)借助magisk临时修改ro.debuggable的值为1,重启会失效
    magisk是一款非常强大的工具,但安装起来似乎没有太简单,不过在google原生手机中安装还是挺简单的,直接修改通过修改boot.img文件再重刷的方式即可安装,boot.img可以在对应版本的刷机包中可获取,或者另一个已经root的且内核版本相同的手机中提取。另外也可以通过三方recovery的方式安装。
    安装完magisk后,原先非root手机就已经具备root功能了,然后修改ro.debuggable的方式如下:

    adb shell #adb进入命令行模式
    su #切换至超级用户
    magisk resetprop ro.debuggable 1
    stop;start; #一定要通过该方式重启
    

    该方法在手机重启后会失效。

    (3)借助magisk永久修改ro.debuggable的值为1
    安装magisk的模块MagiskHide Props Config 模块,安装完成后重启,然后如下执行命令:

    adb shell
    props  # 非root权限下就可以,然后按以下说明操作
    # 选择 Edit MagiskHide Props,序号可能是3或4
    # 之后选择 1-ro.debuggable
    # 重启手机
    getprop ro.debuggable #此时查看 ro.debuggable 是1
    

    只能说,Magisk的功能太强大了。
    参考: Android修改ro.debuggable 的四种方法

    三. 技术总结

    (1)JEB和smalidea+IDEA用于安卓Java层调试,二者的各自优点主要如下:
    1)JEB调试时方便随时看JAVA代码,不过单步时还得跳回smali代码界面;
    2)smalidea+IDEA调试时相对较稳定,并且查看变量比较方便。
    (2)IDA主要用于调试安卓的so文件,当然IDA也可用于调试Linux中so和Mac中so,功能是飞航的强大。

    展开全文
  • 分压偏置共射放大电路的动态分析 首先获得交流通路,将交流通路中的三极管替换成 h 参数等效模型就可得到微变等效电路。 输入电阻由于RB1和RB2通常远远大于rbe,所以约等于rbe。 RB1和RB2串联分压确定基极电位VB,...

    温度变化、三极管老化、电源电压波动等外部因素的影响下,将引起静态工作点的变动,严重时将使放大电路不能正常工作,其中影响最大的是温度的变化

    在这里插入图片描述
    这样一个共射放大电路,从晶体管内部电流的分配关系上,知道上式。基于他的直流通路,我们知道 IB 等于UCC减去UBE 比上RB。在这个式子里,电源电压UCC和电阻RB 都是性能比较稳定的器件,可以认为在温度变化的时候,两个参数不会出现变化。而其他另外三个参数,β、UBE和 ICBO 都是对温度敏感的参数,

    ★ 温度对UBE、β 和 ICBO 的影响的影响

    温度的升高,会使得输入特性曲线,向左移动。也就是温度每升高一摄氏度,温度每升高 1度,UBE将减小 -(2~2.5)mV。温度每升高一摄氏度,β 就将增大0.5%-1%。这就意味着当温度升高的时候,输出特性曲线会向上移动,同时间距会拉大。而由于ICBO是由少子漂移产生的反向电流,因此它的温度就更加敏感了。温度每增加十摄氏度。ICBO就像增大一倍。由此可见,当温度升高的时候UBE 会下降,β 和ICBO会增大。这样的变化带入IC 的表达式,就会发现,当温度升高的时候,客观产生的现象是IC 将会增大。而这反映在我们的特性曲线上就可以发现,当温度升高的时候,静态工作点将会随着特性曲线的向上移动,而沿着负载线上移

    稳定静态工作点的途径

    (1)从元件入手
    选择温度性能好的元件;
    经过一定的工艺处理以稳定元件的参数,防止器件老化。

    (2)从环境入手
    采用恒温措施

    (3)从电路改进入手
    采用温度补偿
    引入反馈

    稳定静态工作点的典型电路及其原理

    稳定静态工作点的思路就是在温度升高的时候减小 IB 从而把本应升高的 IC 再降下来。

    (1)二极管温度补偿电路

    在这里插入图片描述
    在固定偏置电路中,基于基尔霍夫电流定律,在基极RB 节点上进行分流,就可以达到减小 Ib 的效果。基于此可以利用同样对温度敏感的元件。例如,二极管来构成温度补偿电路。此时基于基尔霍夫电流定律,IRb = IR+ IB 。而由于固定偏置电路的 IRb 基本确定,当温度升高的时候在引起 IC 增大的同时,根据二极管的特性分析,温度升高会导致二极管的反向电流 IR 增大,由于IRB 固定不变,IB 自然就会减小,而 IC 等于βIB 将本应升高的 IC 降下来,保持了静态工作点的稳定。

    (2) 直流负反馈Q点稳定电路

    在这里插入图片描述
    在这里插入图片描述
    此时IB 不在是与温度无关的量,由于β 的出现,使得当温度升高的时候,IC 变大的同时,β 也会增大,就会导致 IB 减小,从而将本应升高的 IC 降下来,起到了稳定静态工作点的效果。

    在此过程中,Re 是关键,正是Re 响应了 IC 的变化,在 IC 增大的时候抬高了射极电位Ve 。减小了IB,达到了稳定静态工作点。在这里插入图片描述
    在这里插入图片描述
    将RB1 和RB2 取代了原来的基极电阻RB,对于电源UCC 来说,RB1 和RB2 是一种串联分压的形式。故此电路就叫做分压偏置共射放大电。如果合理地选择各种器件RB1 和RB2,使得电路中的电流和电压满足 I2 >>IB ,VB >>UBE,I2 也就是RB2 上的电流远远大于基极电流 IB ,而 VB 也就是基极电位远远大于UBE,那么就可以通过VB 点的基尔霍夫电流定律,就可以认为基极这条支路视为开路。基于左边支路的串连分压关系,就可以上图中 基极电位 VB 的表达式。通过此式可以看出VB 都是由电阻、电源确定的,都是与温度无关的比较稳定的元件,所以在这种情况下,温度变化的时候基极电位基本恒定。在此前提下,当温度升高的时候,IC 将会增大。而IC ≈ IE , IE 是RE上的电流,必然导致 RE 上的电压降会增大,也就是会抬高射极电位VE 。由于基极电位VB 是几乎与温度无关的一个固定量,所以VB 减 VE ,也就是UBE 将会出现下降的趋势。从而根据晶体管的特性曲线知道UBE 变小 IB 自然就会变小,从而最后将本应升高的集电极电流 IC 降下来,起到稳定静态工作点的作用。通过此过程可以看到,这个分压偏置稳定静态工作点主要有两方面,一个是通过串联分压稳定了基极电位VB ,而另一个则是有赖于RE 引入的直流负反馈

    (3)引入负反馈和温度补偿稳定Q点

    将以上两种方法结合起来,一起达到稳定静态工作点的目的。例如下图中的两个电路就是采用了二极管和热敏电阻进行温度补偿,同时结合RE 的直流反馈来稳定静态工作点。

    在这里插入图片描述
    这里需要注意的是在这样的二极管的补偿电路中,二极管的连接方式和之前的二极管连接方式是不同的,它在阳极接在基极上。此时利用的是二极管正向特性对温度的敏感性。根据二极管温度特性当温度升高的时候,二极管的正向特性将左移。此意味着二极管的端电压UD 将下降。那这样一来,由于二极管正极节点的电压减小,必然会使得基极电压VB 也变小,同时由于射极电阻RE 的存在,使得温度升高的时候,射极电位VE 将会被抬高 。一增一减,从而使得UBE 变小,UBE 的减小带来 IB 减小,最终使得 IC 减小,稳定静态工作点。

    分压偏置共射放大电路的静态分析

    在这里插入图片描述
    方法一 戴维南等效电路法

    首先可以将输入回路视为一个有源的二光头网络,就可以利用戴维南等效定理将其等效为一个电压源和电阻的串联,根据戴维南定理,这个等效电阻RB 应该是这样一个有源网络中将信号源置0 以后的等效电阻,将VCC 对地短路,就可以知道此时的等效电阻RB 显然是RB1 并上RB2,电源UB是这样一个端口的开路电压,显然是RB1和RB2的对UCC 的串联分压。在这里插入图片描述
    根据输入回路的电压方程,就可以得到唯一的未知数 IBQ 的表达式,进而得到ICQ 和UCEQ 。根据之前结论这个分压偏置之所以能够稳定静态工作点,其中一个重要因素,就是因为基极电位是一个与温度无关的恒定量,我们重点来考察一VB这样一个参数。根据回路的方程,知道VB =UBEQ +(1+β)IB RE ,结合IBQ 的表达式,就可以得出一个非常重要的结论。当(1+β)远远大于RB 的时候,此时VB ≈ UBB ,也就是约等于UCCRB2 /(RB1+RB2。从而满足固定基极电位的需求。因此,这个条件跟上面引入的 I2 >>IB ,VB >>UBE 的条件是等价的。工程上,通常将该关系式作为分压偏置电路的稳定偏置条件,也是选取RB1、 RB2和RE的依据。

    方法二 估算法

    根据我们电路稳定偏置条件,也就是 I2 >>IB ,VB >>UBE,那此时根据VB 节点的基尔霍夫电流定律,基极之路视为开路,在这样一种条件下就可以得到 VB 的表达式,进而在基于RB2、RE支路的电压方程,率先求得 IE 而 IC ≈ IE,反过来,再利用 IC = βIB 的表达式,求出IBQ 最终基于输出回路求取UCEQ 完成静态分析。在这里插入图片描述
    关于RE的讨论

    RE越大,负反馈越强,电路温度稳定性越好
    RE 上的电流就是输出电流IC 。因此RE太大其功率损耗也大
    RE 增大,VE增高,使UCE减小,UCEQ 的位置将会影响最大不失真输出电压,而UCEQ 减小必将导致电路动态范围变窄,减小了最大输出电压幅度。若想在RE 增大的同时任然保持原来的动态范围不变,就必须增大 VCC。因此RE不宜取得太大。在小电流工作状态下, RE可取几百欧到几千欧;大电流工作时, RE为几欧到几十欧。

    分压偏置共射放大电路的动态分析

    首先获得交流通路,将交流通路中的三极管替换成 h 参数等效模型就可得到微变等效电路。在这里插入图片描述
    在这里插入图片描述
    输入电阻由于RB1和RB2通常远远大于rbe,所以约等于rbe

    RB1和RB2串联分压确定基极电位VB,RE引入负反馈稳定静态工作点。

    旁路电容CE 比较大,通常在几十uF左右,在交流作用下可以理想认为他短路。如果没有这个旁电容对放大电路的静态性能没有影响。在这里插入图片描述
    在动态性能方面如果去掉这个旁路电容,RE 就将会出现在微变等效电路中。就会影响放大电路的动态性。首先,看电压放大倍数。方法仍然是相似的,利用 ib 来表示UO 和UI,进而得到电压放大倍数。通过输出回路,可以看到UO 是RC和RL 两个并联电阻上的电压,而两者的总电流就 βib,所以仍然可以得到上图中uo的表达式,再来看看输入电压 ui 。ib 是蓝线支路上的电流,ui 则是上下两点之间的电压降,所以就可以用上图中ui 方程用 ib 来描述 ui,而这部分的电压显然有两部分组成,一部分是 rbe 上的电压降,是rbe ib ,另外一部分则是RE 上的电压降,这里要注意RE上的电流是(1+β)IB,写出表达式就反映了ui 和 ib 的关系。将两者相除,根据定义就可以得到这个电路的电压放大倍数如上图所示。显然,跟前面的固定偏置放大电路的电压放大倍数不一样了,而且通常情况下(1+β)RE 远远大于 rbe ,β 和(1+β)又相差无几。经过变化以后,电压放大倍数就是:Au = - R’L /RE。这意味着,此时的电压放大倍数与晶体管的参数没有多大关系,而只与比较稳定的电阻有关,这就意味着电路放大倍数的稳定性得到了大大的提高。在这里插入图片描述
    输入电阻仍然是输入端口看进去的等效电阻,由于RB1 和RB2 的并联支路的阻值已经确定,故Ri = RB1 // RB2 // R’i 。R’i 仍然是端口电压比上端口电流。他的端口电流就是ib, 而端口电压就是Ui 。而Ui 和iB 上已经得到了ui = ibrbe +(1+β) ib RE 这样的表达式,可推出R’i 的表达式是:R’i = rbe+(1+β)RE 。所以这样一种电路的输入电阻就等于下图中的形式。而输出电阻仍然是可以利用三步走的方法来进行求解。求解后的结论仍然是RC在这里插入图片描述将有旁路电容和没有旁路电容的结果加以对比。可以看到,当电路中存在着旁路电容的时候,放大电路的动态性能与固定偏置放大电路没有区别。当去掉旁边的时候,放大倍数出现了变化,是由于分母中(1+β)RE 的存在,使得电压放大倍数减小了。但同时又使得稳定性大大提高了。在显然去掉了旁路电容以后电路的输入电阻大大地提高了,而输出电阻则保持不变。那为什么一个旁路电容就会对电路的性能产生这么大的影响呢?原因就在于,如果没有这个旁路电容CE ,那么RE 就将引入交流负反馈。必然会对电路的动态性能产生各种影响。在这里插入图片描述
    此时我们可以看到,显然,这样一个旁路电容对电路的性能的影响有好有坏,他在提高了稳定性,增大了Ri 的同时,又损失了电压放大倍数。那么在具体的电路的设计中,可以将电阻RE 一分为二,一部分并上旁路电容,那此时显然对交流性能有影响的只有RE1 。那这就是一个比较常用的分压偏置共射放大电路。就可实现放大倍数不会损失过多,又能够在一定程度上抬高输入电阻。

    在这里插入图片描述
    在实际应用中对于这样一个电路,还应该注意以下一些问题

    1. 为了保证分压偏置放大电路能够稳定静态工作点,应合理选择元件参数,满足
      以下两个条件:I2 >>IB VB >>UBE (实际电路中通常取 I2=10IB VB =3UBE
    2. RE不宜取得太大。在小电流工作状态下,可取几百欧到几千欧
    3. 若要调整分压偏置放大电路的静态工作点,通常的方法是调整上偏置电阻RB1
      10IB VB =3UBE
    4. RE不宜取得太大。在小电流工作状态下,可取几百欧到几千欧
    5. 若要调整分压偏置放大电路的静态工作点,通常的方法是调整上偏置电阻RB1
    6. 若分压偏置放大电路的静态工作点正常,而放大倍数严重下降,应重点检查旁路电容CE是否开路或者失效。
    展开全文
  • 程序动态分析工具调研

    千次阅读 2015-10-19 17:03:05
    综述本文是对程序动态工具的调研,通对各种动态分析工具的原理、功能、优缺点等方面的调研分析来使读者在使用工具时更有针对性。 作为调研,本文并不过多的涉及工具的细节,主要关注点在于工的原理、功能、优缺点...

    综述

    本文是对程序动态工具的调研,通对各种动态分析工具的***原理***、功能、***优缺点***等方面的调研分析来使读者在使用工具时更有针对性。
    作为调研,本文并不过多的涉及工具的细节,主要关注点在于工的原理、功能、优缺点(使用领域)。具体工具可做具体了解。

    Gprof

    简介

    Gprof 是GNU gnu binutils工具之一,默认情况下linux系统当中都带有这个工具。Gprof给出了函数调用的次数、调用耗时以及函数的调用关系,通过分析产生的数据结果可以确定程序的执行流程,进而有针对性的对程序进行优化。

    功能

    可以获得的几种格式的数据:1

    1. flat profile :给出了每个函数的耗时以及函数被调用的次数。
    2. call graph:给出了函数调用关系,以及对函数耗时的一个估计。
    3. 注释的源代码--是程序源代码的一个复本,标记有程序中每行代码的执行次数。

    原理

    实现原理2

    gcc -pg 在应用程序的每个函数中添加了名为 mcount/mcount/_mcount的函数。 应用程序每个函数执行时都会执mcount,而mcount则会在内存中保存一张函数调用图,通过函数调用堆栈的形式,查找子函数、父函数的地址,也保存了与函数相关的调用时间、次数等信息。
    程序运行结束后,会在程序退出的路径下生成一个 gmon.out文件。这个文件就是记录并保存下来的监控数据。可以通过命令行方式的gprof或图形化的Kprof来解读这些数据并对程序的性能进行分析。
    另外,如果想查看库函数的profiling,需要在编译是再加入“-lc_p”编译参数代替“-lc”编译参数,这样程序会链接libc_p.a 库,才可以产生库函数的profiling信息。如果想执行一行一行的profiling,还需要加入“-g”编译参数。

    结果产生与分析

    Gprof结果信息
    图1 Gprof结果信息 3

    用法

    1. 在编译和链接时 加上-pg选项。一般我们可以加在 makefile 中。
    2. 执行编译的二进制程序。执行参数和方式同以前。
    3. 在程序运行目录下 生成 gmon.out 文件。如果原来有gmon.out 文件,将会被重写。
    4. 结束进程。这时 gmon.out 会再次被刷新。
    5. 用 gprof 工具分析 gmon.out 文件。

    优缺点4

    ###优点

    1. Gprof为GNU binutils工具之一,默认情况下linux系统当中都带有这个工具,使用方便。
    2. 生成结果包括函数调用时间以及函数调用关系,可以方便用户利用该数据做进一步分析 。

    缺点

    1. 使用插桩技术,消耗系统资源。函数的每次执行都会调用插桩函数mcount,并且mcount函数会在内存中维护一个函数调用图,使得对CPU和内存资源都带来消耗。
    2. 程序必须是正常退出才能生成gmon.out文件,也就是说程序必须执行到main函数的return或者exit()。
    3. 如果程序运行的时间非常短,则Gprof可能无效,因为受到启动、初始化、退出等函数运行时间的影响。
    4. 不支持多进程,如果分析多进程程序则可能一个进程的gmont.out文件会覆盖另一个进程的gmont.out文件。 解决方法是在执行程序之前执行:export GMON_OUT_PREFIX=x.out 则之后生成的文件名就如x.out.pid,多进程的gmon.out就不会相互覆盖。
    5. 不支持多线程。缘故是gprof使用ITIMER_PROF定时器, 当超时时由内核向应用程序发送信号。但多线程程序只有主线程接收ITIMER_PROF。 这里有一个简单的实现方法: 对pthread_create进行包装,并以动态库的形式在程序运行前加载。
    6. 只能分析应用程序在运行过程中所消耗掉的用户时间,无法得到程序内核空间的运行时间。

    Ftrace

    简介56

    ftrace 的作用是帮助开发人员了解 Linux 内核的运行时行为,以便进行故障调试或性能分析。最早 ftrace 是一个 function tracer,仅能够记录内核的函数调用流程。如今 ftrace 已经成为一个framework,采用 plugin (以下一般称为tracer)的方式支持开发人员添加更多种类的 trace 功能。
    ftrace一个鲜明的特点就是,对所有的操作都是对文件的操作,比如,使用某一个tracer便将相应的函数名写入current_tracer文件中,# echo function tracer > current_tracer.

    功能

    ftrace作为一个平台,采用插件的方式支持开发人员添加自定义的trace功能,简而言之,开发人员可以根据自己的需求来使用已有功能或者根据ftrace提供的API来开发满足自己需求的插件。ftrace自带插件如下表6

    插件功能描述
    function tracer仅能够记录内核的函数调用流程
    Schedule switch tracer跟踪进程调度情况
    Wakeup tracer跟踪进程的调度延迟,即高优先级进程从进入 ready 状态到获得 CPU 的延迟时间。该 tracer 只针对实时进程。
    Irqsoff tracer当中断被禁止时,系统无法相应外部事件,比如键盘和鼠标,时钟也无法产生 tick 中断。这意味着系统响应延迟,irqsoff 这个 tracer 能够跟踪并记录内核中哪些函数禁止了中断,对于其中中断禁止时间最长的,irqsoff 将在 log 文件的第一行标示出来,从而使开发人员可以迅速定位造成响应延迟的罪魁祸首。
    Preemptoff tracer和前一个 tracer 类似,preemptoff tracer 跟踪并记录禁止内核抢占的函数,并清晰地显示出禁止抢占时间最长的内核函数。
    Preemptirqsoff tracer同上,跟踪和记录禁止中断或者禁止抢占的内核函数,以及禁止时间最长的函数。
    Branch tracer跟踪内核程序中的 likely/unlikely 分支预测命中率情况。 Branch tracer 能够记录这些分支语句有多少次预测成功。从而为优化程序提供线索。
    Hardware branch tracer利用处理器的分支跟踪能力,实现硬件级别的指令跳转记录。在 x86 上,主要利用了 BTS 这个特性。
    Initcall tracer记录系统在 boot 阶段所调用的 init call 。
    Mmiotrace tracer记录 memory map IO 的相关信息。
    Power tracer记录系统电源管理相关的信息。
    Sysprof tracer缺省情况下,sysprof tracer 每隔 1 msec 对内核进行一次采样,记录函数调用和堆栈信息。
    Kernel memory tracer内存 tracer 主要用来跟踪 slab allocator 的分配情况。包括 kfree,kmem_cache_alloc 等 API 的调用情况,用户程序可以根据 tracer 收集到的信息分析内部碎片情况,找出内存分配最频繁的代码片断,等等。
    Workqueue statistical tracer这是一个 statistic tracer,统计系统中所有的 workqueue 的工作情况,比如有多少个 work 被插入 workqueue,多少个已经被执行等。开发人员可以以此来决定具体的 workqueue 实现,比如是使用 single threaded workqueue 还是 per cpu workqueue。
    Event tracer跟踪系统事件,比如 timer,系统调用,中断等。

    注意:

    1. 这里只是列出了比较常用的tracer,并没有列出所有的tracer,ftrace 是目前非常活跃的开发领域,新的 tracer 将不断被加入内核。
    2. available_tracers文件记录了当前编译进内核的跟踪器的列表,换句话说,默认情况下,用户的机器上并不支持上面所有tracer。

    原理

    实现原理

    Ftrace 有两大组成部分,一是 framework,另外就是一系列的 tracer 。每个 tracer 完成不同的功能,它们统一由 framework 管理。 ftrace 的 trace 信息保存在 ring buffer 中,由 framework 负责管理。 Framework 利用 debugfs 系统在 /debugfs 下建立 tracing 目录,并提供了一系列的控制文件。其架构图如下:
    ftrace架构图
    图2 ftrace实现原理6
    Ftrace本身也使用的是插桩技术, 原理类似于Gprof,但是ftrace没有在内存中保存函数调用图,并且动态地使用mcount指令,只是在用户需要时替换nop指令为mcount指令7。具体操作上,ftrace 采用 GCC 的 profile 特性在所有内核函数的开始部分加入一段 stub 代码,ftrace 重载这段代码来实现 trace 功能。gcc 的 -pg 选项将在每个函数入口处加入对 mcount 的调用代码。

    结果产生与分析

    由于ftrace针对不同的应用场景有不同的tracer来完成相应的工作,故而,各个tracer返回来的数据格式也不尽相同。这里仅以ftrace中最常用的function tracer为例6

    # tracer: function 
     # 
     #  TASK-PID   CPU#    TIMESTAMP        FUNCTION 
     #   |  |       |          |                | 
      bash-4251  [01]  10152.583854:    path_put <-path_walk 
      bash-4251  [01] 10152.583855: dput <-path_put 
      bash-4251  [01] 10152.583855: _atomic_dec_and_lock <-dput
    

    可以看到,tracer 文件类似一张报表,前 4 行是表头。第一行显示当前 tracer 的类型。第三行是 header 。对于 function tracer,该表将显示 4 列信息。首先是进程信息,包括进程名和 PID ;第二列是 CPU,在 SMP 体系下,该列显示内核函数具体在哪一个 CPU 上执行;第三列是时间戳;第四列是函数信息,缺省情况下,这里将显示内核函数名以及它的上一层调用函数。通过对这张报表的解读,用户便可以获得完整的内核运行时流程。这对于理解内核代码也有很大的帮助。有志于精读内核代码的读者,或许可以考虑考虑 ftrace 。如上例所示,path_walk() 调用了 path_put 。此后 path_put 又调用了 dput,进而 dput 再调用 _atomic_dec_and_lock 。

    用法

    传统的用法流程大体如下:68

    1. 编译内核使得内核支持所需要的trace。注意,ftrace是内核自带的分析工具,如没有特需的需求可不进行此步。
    2. 挂载debugfs,# mount -t debugfs nodev /sys/kernel/debug。debugfs虚拟文件系统是内核空间和用户空间数据通信的工具,挂载后,挂载点目录下包含了ftrace相应的文件。比如,记录当前可用tracer的文件available_tracers就在其中。
    3. 切换到目录 /sys/kernel/debug/tracing/ 下。
    4. 查看 available_tracers 文件,获取当前内核支持的跟踪器列表。
      5. 关闭 ftrace 跟踪,即将 0 写入文件 tracing_enabled。# echo 0 > tracing_enabled在新的内核版本中,tracing_enabled 被删除了,也就是说这步是不需要的,同理第9步关于tracing_enabled部分也是不需要的。关于原因9,有人问过 Ftrace 的维护人Steven Rostedt,他说使用 tracing_on 可以快速的打开 Ftrace 的追踪,这让 tracing_enabled 显得很轻量级或者说显得比较冗余,下面可以会说到,我们写内核程序时可以使用Ftrace 提供的内核函数 tracing_on() or tracing_off() 直接打开追踪,这其实就是使用的 tracing_on ,所以在新内核中 tracing_enabled 这个看起来比较冗余的选项已经被删除
    5. 激活 ftrace_enabled ,否则 function 跟踪器的行为类似于 nop;另外,激活该选项还可以让一些跟踪器比如 irqsoff 获取更丰富的信息。建议使用 ftrace 时将其激活。要激活 ftrace_enabled ,可以通过 proc 文件系统接口来设置:# echo 1 > /proc/sys/kernel/ftrace_enabled
    6. 将所选择的跟踪器的名字写入文件 current_tracer。# echo funtion tracer > current_tracer
    7. 跟踪函数过滤。 将要跟踪的函数写入文件 set_ftrace_filter ,将不希望跟踪的函数写入文件 set_ftrace_notrace。通常直接操作文件 set_ftrace_filter 就可以了。
      9. 激活 ftrace 跟踪,即将 1 写入文件 tracing_enabled。还要确保文件 tracing_on 的值也为 1,该文件可以控制跟踪的暂停如果是对应用程序进行分析的话,启动应用程序的执行,ftrace 会跟踪应用程序运行期间内核的运作情况。
    8. 通过将 0 写入文件 tracing_on 来暂停跟踪信息的记录,此时跟踪器还在跟踪内核的运行,只是不再向文件 trace 中写入跟踪信息;或者将 0 写入文件 tracing_enabled 来关闭跟踪。
    9. 查看文件 trace 获取跟踪信息,对内核的运行进行分析调试。

    优缺点

    优点

    1. 执行选择性插桩,而非对所有的函数进行插桩,即,动态的使用mcount函数,只是在用户需要的时候将nop替换为mcount,这样就可以有针对的进行函数分析7
    2. ftrace不需要将函数调用图保存在内存中,这样就减轻了内存资源的消耗7
    3. ftrace作为一个framework,本身自带了各种特定功能的tracer,用户可以直接使用。同时,用户也可以根据自己的需求修改已有tracer或者调用ftrace提供的API编写复合自己需求的tracer6

    缺点

    1. ftrace虽然执行的是选择性插桩技术,但是还是会影响到程序本身性能。

    SystemTap

    简介

    SystemTap 是监控和跟踪运行中的 Linux 内核的操作的动态方法。这句话的关键词是动态,因为SystemTap 没有使用工具构建一个特殊的内核,而是允许您在运行时动态地安装该工具。它通过一个名为Kprobes 的应用编程接口(API)来实现该目的。
    Kprobe机制,可以用来动态地收集调试和性能信息的工具,是一种非破坏性的工具,用户可以用它跟踪运行中内核任何函数或执行的指令等。相比之前的做法已经有了质的提高了,但Kprobe并没有提供一种易用的框架,用户需要自己去写模块,然后安装,对用户的要求还是蛮高的。
    相比Kprobe,systemtap更加简单,提供给用户简单的命令行接口,以及编写内核指令的脚本语言。对于开发人员,systemtap是一款难得的工具。

    功能

    利用Kprobe机制动态的收集函数调用和程序性能相关的信息,以此来实现动态地监控和跟踪运行中的Linux内核。

    原理

    实现原理

    SystemTap 用于检查运行的内核的两种方法是 Kprobes 和 返回探针。但是理解任何内核的最关键要素是内核的映射,它提供符号信息(比如函数、变量以及它们的地址)。有了内核映射之后,就可以解决任何符号的地址,以及更改探针的行为。
    Kprobes 从 2.6.9 版本开始就添加到主流的 Linux 内核中,并且为探测内核提供一般性服务。它提供一些不同的服务,但最重要的两种服务是 Kprobe 和 Kretprobe。Kprobe 特定于架构,它在需要检查的指令的第一个字节中插入一个断点指令。当调用该指令时,将执行针对探针的特定处理函数。执行完成之后,接着执行原始的指令(从断点开始)。
    Kretprobes 有所不同,它操作调用函数的返回结果。注意,因为一个函数可能有多个返回点,所以听起来事情有些复杂。不过,它实际使用一种称为 trampoline 的简单技术。您将向函数条目添加一小段代码,而不是检查函数中的每个返回点。这段代码使用 trampoline 地址替换堆栈上的返回地址 —— Kretprobe 地址。当该函数存在时,它没有返回到调用方,而是调用 Kretprobe(执行它的功能),然后从 Kretprobe 返回到实际的调用方。
    systemtap 的核心思想是定义一个事件(event),以及给出处理该事件的句柄(Handler)。当一个特定的事件发生时,内核运行该处理句柄,就像快速调用一个子函数一样,处理完之后恢复到内核原始状态。这里有两个概念:
    事件(Event): systemtap 定义了很多种事件,例如进入或退出某个内核函数、定时器时间到、整个systemtap会话启动或退出等等。
    ***句柄(Handler):***就是一些脚本语句,描述了当事件发生时要完成的工作,通常是从事件的上下文提取数据,将它们存入内部变量中,或者打印出来。
    Systemtap 工作原理是通过将脚本语句翻译成C语句,编译成内核模块。模块加载之后,将所有探测的事件以钩子的方式挂到内核上,当任何处理器上的某个事件发生时,相应钩子上句柄就会被执行。最后,当systemtap会话结束之后,钩子从内核上取下,移除模块。整个过程用一个命令 stap 就可以完成。
    systemtap流程图
    图 3 SystemTap流程图

    数据产生与分析

    由于在使用SystemTap时,用户通过其提供的配套脚本语言来实现自己所需功能,所以数据的产生和分析往往也是千差万别的。往往用户通过SystemTap提供的API获取自己想要的数据,根据自己的需求对其进行格式化处理以便对其进行特定的分析。

    用法

    SystemTap的用法比较简单灵活性也比较强,用根据其通过的脚本语言规则和相应的API就可以很方便的得到自己想要的数据,并且按照自己需要的格式进行输出。这里,以一个监控 sync 系统调用应用作为例子10
    注意: 同Ftrace一样SystemTap的使用需要获取到也行系统的调试信息,在一般的Linux发行版本这些调试信息是被关闭的所以需要重新编译内核并将这些需要的调试选项勾选。一种更文件简单的方法是直接现在按照debug版本的内核。具体如何操作已经超出本文范围,读者可以参见参考文献11给出的相关资料。

    global syscalllist
    
    probe begin {
      printf("System Call Monitoring Started (10 seconds)...\n")
    }
    probe syscall.*
    {
      syscalllist[pid(), execname()]++
    }
    probe timer.ms(10000) {
      foreach ( [pid, procname] in syscalllist ) {
        printf("%s[%d] = %d\n", procname, pid, syscalllist[pid, procname] )
      }
      exit()
    }
    

    脚本包含一个全局变量定义和 3 个独立的探针。在首次加载脚本时调用第一个探针(begin 探针)。在这个探针中,您可以发出一条表示脚本在内核中运行的文本消息。接下来是一个 syscall 探针。注意这里使用的通配符 (*),它告诉 SystemTap 监控所有匹配的系统调用。当该探针触发时,将为特定的 PID 和进程名增加一个关联数组元素。最后一个探针是 timer 探针。这个探针在 10,000 毫秒(10 秒)之后触发。与这个探针相关联的脚本将发送收集到的数据(遍历每个关联数组成员)。当遍历了所有成员之后,将调用 exit 调用,这导致卸载模块和退出所有相关的 SystemTap 进程。
    脚本的输出如下所示。从这个脚本中您可以看到运行在用户空间中的每个进程,以及在 10 秒钟内发出的系统调用的数量。

    $ sudo stap profile.stp
    System Call Monitoring Started (10 seconds)...
    stapio[16208] = 104
    gnome-terminal[6416] = 196
    Xorg[5525] = 90
    vmware-guestd[5307] = 764
    hald-addon-stor[4969] = 30
    hald-addon-stor[4988] = 15
    update-notifier[6204] = 10
    munin-node[5925] = 5
    gnome-panel[6190] = 33
    ntpd[5830] = 20
    pulseaudio[6152] = 25
    miniserv.pl[5859] = 10
    syslogd[4513] = 5
    gnome-power-man[6215] = 4
    gconfd-2[6157] = 5
    hald[4877] = 3
    $
    

    优缺点

    优点

    1. SystemTap没有使用工具构建一个特殊的内核,而是采用在运行时动态地安装该工具,它通过一个名为Kprobe的应用编程接口(API)来实现动态安装。
    2. SystemTap提供语法结构比较简单的脚本语言,可以使的用户根据自己的需求实现相应的脚本来获取相应的数据。

    缺点

    1. SystemTap 项目是 Linux 社区对 SUN Dtrace 的反应,目标是达到甚至超越 Dtrace 。因此 SystemTap 设计比较复杂,Dtrace 作为 SUN 公司的一个项目开发了多年才最终稳定发布,况且得到了 Solaris 内核中每个子系统开发人员的大力支持。 SystemTap 想要赶超 Dtrace,困难不仅是一样,而且更大,因此她始终处在不断完善自身的状态下,在真正的产品环境,人们依然无法放心的使用她。不当的使用和 SystemTap 自身的不完善都有可能导致系统崩溃6
    2. 需要支持某种编程接口让用户自定义 trace 行为,这无疑使得用户必须对其有深入的理解,提高了使用门槛,并且需要用户编写大量的脚本,这也增加了用户的工作量。

    总结

    通过对Gprof、Ftrace、SystemTap三个工具的调用,我们不难得出如下结果:

    工具功能完备性易用性工具稳定性
    Gprof+++
    SystemTap++++++
    Ftrace+++++++++

    虽然,这些系统内核自带的工具有些功能已经很强大,但是这些工具的使用前提都是系统必须是完全启动的,也就是说对于系统启动过程中的内核状态函数的调用是完全无能为力的。如果要分析系统从启动到运行整个过程的状态必须借助其他工具如S2E等

    关注作者公众号

    在这里插入图片描述

    参考文献


    1. 《GNU Gprof》:https://sourceware.org/binutils/docs-2.17/gprof/index.html ↩︎

    2. 《gprof使用和介绍》: http://blog.sina.com.cn/s/blog_4a471ff601013vud.html ↩︎

    3. 《Linux性能评测工具之一:gprof篇》: http://blog.csdn.net/stanjiang2010/article/details/5655143 ↩︎

    4. 《用gprof分析程序性能》: http://www.berlinix.com/dev/gprof.php ↩︎

    5. 《ftrace - Function Tracer》:https://www.kernel.org/doc/Documentation/trace/ftrace.txt ↩︎

    6. 《ftrace简介》:https://www.ibm.com/developerworks/cn/linux/l-cn-ftrace/ ↩︎ ↩︎ ↩︎ ↩︎ ↩︎ ↩︎ ↩︎

    7. 《基于内核跟踪的动态函数调用图生成方法》向 勇 ,汤卫东 ,杜香燕 ,孙卫真 ↩︎ ↩︎ ↩︎

    8. 《使用ftrace 调试Linux 内核,第2 部分》:http://www.ibm.com/developerworks/cn/linux/l-cn-ftrace2/ ↩︎

    9. 《 Linux内核调试工具 Ftrace 进阶使用手册》:http://blog.csdn.net/longerzone/article/details/16884703 ↩︎

    10. 《Linux自检和SystemTap》:https://www.ibm.com/developerworks/cn/linux/l-systemtap/ ↩︎

    11. 《内核检测工具SystemTap简介》: http://www.cnblogs.com/hazir/p/systemtap_introduction.html#top ↩︎

    展开全文
  • 算法设计与分析动态规划

    万次阅读 多人点赞 2019-02-11 16:59:36
    在实际应用中可以按以下几个简化的步骤进行设计: (1)分析最优解的性质,并刻画其结构特征。 (2)递归地定义最优解。 (3)以自底向上或自顶向下的记忆化方式计算出最优值。 (4)根据计算最优值时得到的信息...

    分享一个大牛的人工智能教程。零基础!通俗易懂!风趣幽默!希望你也加入到人工智能的队伍中来!请点击http://www.captainbed.net

    动态规划(Dynamic Programming,DP)是将多阶段决策问题进行公式化的一种技术,是算法设计方法之一。

    动态规划的原理

    动态规划是一种解决多阶段决策问题的优化方法,把多阶段过程转化为一系列单阶段问题,利用各阶段之间的关系逐个求解。

    动态规划求解的基本步骤

    采用动态规划求解的问题一般要具有以下3个性质

    (1)最优性原理:如果问题的最优解所包含的子问题的解也是最优的,就称该问题具有最优子结构,即满足最优性原理。

    (2)无后效性:即某个阶段的状态一旦确定,就不受这个状态以后决策的影响。也就是说,某个状态以后的过程不会影响以前的状态,只与当前状态有关。

    (3)有重叠于问题:即子问题之间是不独立的,一个子问题在下一阶段决策中可能被多次使用。

    动态规划所处理的问题是一个多阶段决策问题,一般由初始状态开始,通过对中间阶段决策的选择,达到结束状态。这些决策形成了一个决策序列,同时确定了完成整个过程的活动路线。

    动态规划的设计都有着一定的模式,一般要经历以下几个步骤

    (1)划分阶段:按照问题的时间或空间特征把问题划分为若干个阶段。在划分阶段时注意划分后的阶段一定是有序的或者是可排序的,否则问题无法求解。

    (2)确定状态和状态变量:将问题发展到各个阶段时所处的各种客观情况用不同的状态表示出来。当然,状态的选择要满足无后效性。

    (3)确定决策并写出状态转移方程:因为决策和状态转移有着天然的联系,状态转移就是根据上一阶段的状态和决策来推导出本阶段的状态。所以如果确定了决策,状态转移方程也就可以写出。但事实上常常是反过来做,根据相邻两个阶段的状态之间的关系来确定决策和状态转移方程。

    (4)寻找边界条件:给出的状态转移方程是一个递推式,需要一个递推的终止条件或边界条件。一般情况下只要解决问题的阶段、状态和确定状态转移决策,就可以写出状态转移方程(包括边界条件)。

    在实际应用中可以按以下几个简化的步骤进行设计

    (1)分析最优解的性质,并刻画其结构特征。

    (2)递归地定义最优解。

    (3)以自底向上或自顶向下的记忆化方式计算出最优值。

    (4)根据计算最优值时得到的信息构造问题的最优解。

    注意:动态规划是一种求解思路,注重决策过程,不同的问题得到的模型可能不一样,关键是掌握其原理,利用递推关系求最优解。

    展开全文
  • BitBlaze(四) - 动态分析组件TEMU

    千次阅读 2013-05-02 11:20:16
    4 TEMU:动态分析组件 这一部分主要介绍TEMU,BItBlaze平台的动态分析组件,描述其提取操作系统级语义的组件,执行系统全局的动态污点分析,以及它的插件和实现。 4.1 TEMU概述 TEMU是一个基于全系统仿真器QEMU...
  • Android APK 静态分析与动态分析

    千次阅读 2016-10-25 09:52:52
     动态分析是Android沙盘的主要功能,主要使用Google Android模拟器作为沙盘环境,同时以前面修改过的system.img来启动模拟器,以在操作过程中生成我们所需的日志信息:   system(' start emulator -...
  • Java JDK 动态代理(AOP)使用及实现原理分析

    万次阅读 多人点赞 2019-05-08 21:28:06
    二、Java 动态代理类 三、JDK的动态代理怎么使用? 四、动态代理怎么实现的? 五、结论 一、什么是代理? 代理是一种常用的设计模式,其目的就是为其他对象提供一个代理以控制对某个对象的访问。代理类负责为...
  • iOS静态方法动态方法

    千次阅读 2015-09-19 11:00:24
     iOS中有静态方法动态方法,那么两种方法的异同是什么? 2、问题分析  因为每个对象都由相应的数据结构与方法相构成,一个程序可能有多个属于同一个类的对象,而每个对象的数据结构应该是不一的,但方法是相同...
  • 动态规划中递推式的求解方法不是动态规划的本质。 我曾经作为省队成员参加过NOI,保送之后也给学校参加NOIP的同学多次讲过动态规划,我试着讲一下我理解的动态规划,争取深入浅出。希望你看了我的答案,能够喜欢上...
  • 静态分析方法简介

    千次阅读 2018-02-07 16:24:14
    程序分析分为动态分析和静态分析两种,其中静态分析是指不实际运行程序而通过词法分析、语法分析、控制流、数据流等技术对源码进行扫描分析 本文从宏观上对静态分析技术做一个大体的介绍,并为后续文章做一个好的...
  • Java动态代理分析

    万次阅读 多人点赞 2017-04-12 20:27:16
    Java动态代理机制的出现,使得Java开发人员不用手工编写代理类,只要简单地制定一组接口及委托类对象,便能动态地获得代理类。代理类会负责将所有的方法调用分配到委托对象上反射执行,配置执行过程中,开发人员还...
  • 模糊聚类分析方法

    万次阅读 多人点赞 2019-05-07 08:33:20
    【3】模糊聚类分析方法:模糊等价矩阵、模糊相似矩阵、传递闭包法、布尔矩阵法 【4】模糊决策分析方法 在工程技术和经济管理中,常常需要对某些指标按照一定的标准(相似的程度或亲 疏关系等)进行分类处理...
  • 动态代理及JDK动态代理源码分析

    千次阅读 2014-04-14 23:16:41
    JAVA的动态代理机制可以动态的创建代理并动态的处理代理方法调用,只要简单指定一组接口及为拖累对象,就能动态的获取代理类
  • 动态污点分析浅述

    万次阅读 2016-09-13 22:13:09
     动态污点分析(Dynamic Taint Analysis)是近几年刚刚被提出的一种新的有效检测各种蠕虫攻击和自动提取特征码用于IDS和IPS的一系列解决方案。其原理主要分为两大部分:动态污点标记和非法操作检测、以及更精确的...
  • java动态代理中的invoke方法是如何被自动调用的

    千次阅读 多人点赞 2016-09-06 15:41:10
    转载声明:本文转载至 zcc_0015的专栏 一、动态代理与静态代理的区别。 (1)Proxy类的代码被固定下来,不会因为业务的逐渐庞大而庞大;...静态代理这个模式本身有个大问题,如果类方法数量越来越多的时候,代理
  • 数据分析方法汇总

    千次阅读 2014-12-31 10:15:24
    这篇文章是从人大经济论坛转载过来的,留下来以做备用,在此谢谢作者的辛苦整理 一、描述统计 ...2、正态性检验:很多统计方法都要求数值服从或近似服从正态分布,所以之前需要进行正态性检验。常用方
  • 面向对象的分析方法

    千次阅读 2015-05-11 21:55:16
    OOA所强调的是在系统调查资料的基础上,针对OO方法所需要的素材进行的归类分析和整理,而不是对管理业务现状和方法分析。  OOA(面向对象的分析)模型由5个层次(主题层、对象类层、结构层、属性层和服务层)和5...
  • 自己的理解:生成代理类的时候,根据传的Invocationhandler参数 会在代理类的实现接口的方法里面实现InvocationHandler的invoke()方法,也就是调用InvocationHandler实现类的invoke方法,然后在InvocationHandler...
  • 统计学常用的数据分析方法总结

    千次阅读 2019-10-31 15:54:45
    描述统计是通过图表或数学方法,对数据资料进行整理、分析,并对数据的分布状态、数字特征和随机变量之间关系进行估计和描述的方法。描述统计分为集中趋势分析和离中趋势分析和相关分析三大部分。 集中趋势分析 ...
  • 这道题可以用暴力搜索,记忆搜索,动态规划,状态继续化简后的动态规划方法等四种方法! 在面试中出现类似的题目,优化轨迹高度类似! 1、暴力搜索方法 下面先看这道题的暴力搜索方法的过程: 我们认为使用0...
  • 本文介绍两种切换数据库的方法方法1:数据库信息都配置在spring xml中,适用于一般数据库切换。执行完某操作,切换数据库,执行另一个操作。 方法2:将数据库信息配置在默认数据源中,适用于切换数据库操作...
  • 16种常用的数据分析方法汇总

    万次阅读 多人点赞 2017-04-04 16:16:33
    经常会有朋友问到一个朋友,数据分析常用的分析方法有哪些,我需要学习哪个等等之类的问题,今天数据分析精选给大家整理了十六种常用的数据分析方法,供大家参考学习。 一、描述统计 描述性统计是指运用制表和...
  • Java代理和动态代理机制分析和应用

    千次阅读 2015-12-02 19:54:54
    本博文中项目代码已开源下载地址:GitHubJava代理和动态代理机制分析和应用概述代理是一种常用的设计模式,其目的就是为其他对象提供一个代理以控制对某个对象的访问。代理类负责为委托类预处理消息,过滤消息并转发...
  • 所有可疑文件的分析都是在虚拟机中进行的,虚拟机中内置了病毒分析所要用到的各类工具和软件(各类工具详见上一篇博客),根据可疑文件分析的一般流程,对文件进行分析,得出分析结论。 上传漏洞平台检测 分析一...
  • 病毒分析教程第二话--动态行为分析

    千次阅读 2018-07-07 16:12:26
    静态特征分析可以说是分析一个病毒的前奏,属于比较简单的分析分析环节包括:VT检测、编译时间、加壳信息、导入函数、可疑字符串,等等。 Lab 1-1 本节实验使用到两个样本Lab01-01.dll和Lab01-01....
  • 房地产大数据分析方法

    万次阅读 2018-05-04 07:11:43
    房地产大数据分析方法 李万鸿2018 采用大数据辅助房地产分析是大势所趋,提通过对海量数据的分析研究,可以精准地了解政策、城市、市场、土地、住房、价格、用户等各方面因素,并给出智能决策辅助,从而做到...
  • 16种常用的数据统计分析方法汇总

    万次阅读 2019-04-24 16:43:00
    经常会有朋友问到一个朋友,数据分析常用的分析方法有哪些,我需要学习哪个等等之类的问题,今天数据分析精选给大家整理了十六种常用的数据分析方法,供大家参考学习。 (注:这些统计分析方法基本都是统计学的方法...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 329,897
精华内容 131,958
关键字:

以下属于动态分析方法的是