1.浏览器首先发送给服务器它的SSL的版本号和加密偏好(也就是指他们之间将要使用的symmetric key algorithm) 2.服务器给浏览器发送它的SSL版本号,加密偏好和证书。证书中包括了服务器的RSA公钥,且是由某CA认证的。CA认证指的是这个证书需要由CA的私钥进行签名。 (证书产生的过程是服务器把自己的公钥发送给CA,CA加上自己的私钥签名,保证它的完整性,生成证书) 3.浏览器有一个受信CA的列表,列表中有这些CA的公钥。当它收到证书的时候,它需要检测这个CA是否在列表当中。如果不在列表中,浏览器会警告用户通信的不安全。如果在的话,浏览器就使用这个证书得到服务器的公钥。 (浏览器用有信誉CA的公钥解密证书中的服务器公钥,如果这个CA不可信,可能是由某些不安全机构自设的CA,进行欺骗用) 4.浏览器生成了一个对称的session key,然后用服务器的公钥对它进行加密,然后把加密的session key发送给服务器。 (非对称加解密的方式比较耗时,不能把整个数据由这种方式加解密,而只采用它对对称密钥本身就行加解密,以后就使用对称的密钥进行加解密的工作,保证了密钥传递的安全性) 5.浏览器发送一个信息给服务器说未来我们之间的通信用这个session key进行加密。然后发送一个信息说浏览器端握手过程已经结束。 6.服务器给发送一个信息给浏览器说未来我们用这个session key进行加密。然后发送一个信息说服务器端的握手过程已经结束。 7.SSL session开始,服务器和浏览器之间用session key进行加密解密和验证数据完整性。 一个array中所有的元素先升序排列,后降序排列称之为Unimodal,Unimodal Search就是要找到这个最大的值,O(lgn)的做法就是二分法查询,如果所取的元素大于两边的元素,则是最大值,如果左面大,就在左半边取,右面大,则在右半边取,直到取到为止。应用在convex中找端点的最大x坐标和最大y坐标。找最大的x坐标就是在原本的排列中进行Unimodal Search,找最大的y坐标就是从找到的最大的x坐标那个点开始寻找到第一个点,在这些点中进行Unimodal Search。代码片段如下,写的很挫,不过还是能运行的。 1 int middle(int *UnimodalList,int middlenum) 关键词(Tag): unimodal search
内核中的Notification Chains的分析Damocles 发表于 2007-10-27 17:12:53 Linux内核中有许多子系统,他们之间有着非常多的依赖与交互关系,当某一个子系统中有事件发生时,就会影响到其他子系统的工作,比如说网卡ip地址的改变,设备的热插拔等等。Linux内核中使用了Notification Chains的方法来处理这类事件,顾名思义,它是一个链表的数据结构,其中链表的表元由回调函数,priority和next指针组成。
35 struct notifier_block {当我们初始化子系统的时候,应该知道自己到底对哪些事件比较敏感,也就是说知道哪些事件的发生会对自己的功能发生影响,如果有的话,就注册自己到这个特定的notification chain里面去,我们举一个例子来看看: 1242 void __init arp_init(void)这个取自arp的初始化,我们注意最后一行的函数register_netdevice_notifier,这个就是注册函数,当然它还会有多层的调用,而arp_netdev_notifier就是一个notifier_block的结构,其中回调函数初始化为arp_netdev_event。我们先来看一下这个回调函数的实现 1201 static int arp_netdev_event(struct notifier_block *this, unsigned long event, void *ptr)我们看到了,它只关心一种event,那就是NETDEV_CHANGEADDR,其他的事件发生它就并不在意了,当网络设备发生任何已经定义好的事件时,会遍历notification chain来进行遍历通知,如果是我们关心的事件发生,我们就作出相应的反应进行处理,如果不是,那么就当什么都没有发生。 注册函数有一个通用的类型函数,上文所见到的register_netdevice_notifier经过二层调用之后就会遇到,这个函数就是 105 static int notifier_chain_register(struct notifier_block **nl,这个函数的作用就是把一个notifier_block加入到chain中去,不过这个链表的插入方法有点诡异,因为它直接利用了二级指针的一个巧妙应用,一般我们插入链表都需要有一个指针来保存前一个位置,然后再插入表元,而在这里,它只利用了一个指针就完成了这些工作,也就是把这个二级指针保存了前一个表元的next指针。 最后我们来看一下那个事件发生时通知在通知链上的表元的函数 131 static int __kprobes notifier_call_chain(struct notifier_block **nl,这个函数应该很容易理解,就是调用回调函数进行处理。 Notification Chains最重要的好处是每个子系统自己来注册到底需要听哪些事件,而不是事件的发生方来遍历各个子系统来问我的改变你们是不是需要进行相应的对策处理,这样效率就提高了,也就是所谓的publish-and-subscribe model。 这周继续阅读netfilter部分的代码和文档,看了一下netfilter hacking howto和水木上的m文,对前一周一些没有搞懂的问题弄明白了。 主要的一个问题是netfilter是在内核中,那么它和iptables这个基于user space的工具怎么交互呢?其实我们应该这么想,netfilter和table是分开实现的,我们通过协议类型和挂载点来找到的在二维数组nf_hooks的位置上,是一个链表的头指针,它所指向的这个链表中有对于这个特定协议和特定挂载点的对于各个表中规则的处理,这些表包括像filter,nat和mangle之类的表。我们在用户空间中调用iptables时,我们的参数为所针对的table,针对的处理链chain,match的规则,和最终的处理方式target,而它们中每个都能在内核空间找到对应关系,像chain针对的就是挂载点。 我们重新回到nf_hooks数组,我们得到一个处理链表,自然进行遍历,在每个节点上都调用hook函数,hook函数指定为ipt_hook之类的函数,具体需要参照加载的函数,我们只是找出一个进行举例。ipt_hook调用ipt_do_table,这个函数是对table进行操作的,函数很长,我们来看一下。 215 /* Returns one of the generic firewall policies, like NF_ACCEPT. */做一些基本的注释,其实我不喜欢一篇技术博客长篇累牍贴代码,尤其是Linux内核源代码,更多的是希望能够进行分析。但往往越是讨厌的事情,自己往往又这么做了。好吧,还是来解释一下这个函数吧。 它是对table进行操作,至于对于哪个table,是由调用函数决定的。调用之后,他的主要工作如下: 1.找到table的地址,其实重要的是找到ipt_entry的地址,因为里面存着match和target。 2.对match进行匹配,如果匹配成功,则获取target。如果失败,跳转到no_match,找到下一个ipt_entry,进行下一轮匹配。 3.成功的话会有两种情况,一是得到初始化时候的standard target,这时候target函数是初始化为NULL的。二是得到一个由用户新加的target,跟据verdict和hotdrop,来决定是怎么返回。 这边有一点需要指出的是,match的匹配原则是如果这个数据包都匹配了,则不再进行比较,直接可以返回了,只有在no match的情况下才继续匹配下一条match。这个和在上文提到的nf_iterate中的处理方式不同,这个要小心区分的。在同一张表中,是只要匹配就返回verdict,而在nf_iterate 调用钩子函数处理中,如果是ACCEPT的情况,则需要继续处理。天哪,其实这个貌似没有什么特别的联系,只是我自己混淆了一开始,我想大家应该不会像我 这样犯这么低级的错误,写出来算是警戒一下自己。 刚才做了个实验,验证了一下。 实验一: sudo iptables -t filter -A INPUT -j ACCEPT -p tcp sudo iptables -t filter -A INPUT -j DROP -p tcp -s hk-in-f104.google.com 这时候是能访问google的,因为数据包进入钩子函数之后只匹配了第一条就返回了,第二条规则是没有意义的。 实验二: sudo iptables -t filter -A INPUT -j DROP -p tcp -s hk-in-f104.google.com sudo iptables -t filter -A INPUT -j DROP -p tcp 这时候不能访问任何网站,因为google以外任意一个网站第一条不匹配,则进入下一条,然后drop掉,google则第一条就不匹配,直接drop。 这个在ip_do_table的源代码里面就很清楚了。至于表示table的那些源代码,真的是看了厥倒,这种匪夷所思的数据结构,这些hacker们还胆子真够大的,真不怕内存读写错误啊,要是我我可不敢这么写,他们果然是艺高人胆大,这个下次再分析吧,今天还算是差不多搞清楚了。 |
|
来自: jijo > 《iptables》