﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>C++博客-Khan's Notebook    GCC/GNU/Linux Delphi/Window Java/Anywhere-随笔分类-周边技术</title><link>http://www.cppblog.com/Khan/category/777.html</link><description>路漫漫，长修远，我们不能没有钱</description><language>zh-cn</language><lastBuildDate>Wed, 01 May 2024 09:38:21 GMT</lastBuildDate><pubDate>Wed, 01 May 2024 09:38:21 GMT</pubDate><ttl>60</ttl><item><title>关于CppBlog首页CSS样式丢失问题解决办法</title><link>http://www.cppblog.com/Khan/archive/2024/04/30/230338.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Tue, 30 Apr 2024 08:54:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2024/04/30/230338.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/230338.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2024/04/30/230338.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/230338.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/230338.html</trackback:ping><description><![CDATA[管理-&gt;选项-&gt;Configure 的 首页HTML代码中写入
<div style="font-size: 13px; border-top: #cccccc 1px solid; border-right: #cccccc 1px solid; width: 98%; border-bottom: #cccccc 1px solid; word-break: break-all; padding-bottom: 4px; padding-top: 4px; padding-left: 4px; border-left: #cccccc 1px solid; padding-right: 5px; background-color: #eeeeee"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><img src="http://www.cppblog.com/images/OutliningIndicators/None.gif" align="top"  alt="" /><span style="color: #0000ff">&lt;</span><span style="color: #800000">link&nbsp;</span><span style="color: #ff0000">id</span><span style="color: #0000ff">="MainCss"</span><span style="color: #ff0000">&nbsp;type</span><span style="color: #0000ff">="text/css"</span><span style="color: #ff0000">&nbsp;rel</span><span style="color: #0000ff">="stylesheet"</span><span style="color: #ff0000">&nbsp;href</span><span style="color: #0000ff">="https://www.cppblog.com/Skins/AnotherEon001/style.css"</span><span style="color: #ff0000">&nbsp;</span><span style="color: #0000ff">/&gt;</span></div><br />应该是某位大佬加了https证书后忘记将页面内的css样式链接改成https了, 导致该资源被浏览器拦截<img src ="http://www.cppblog.com/Khan/aggbug/230338.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2024-04-30 16:54 <a href="http://www.cppblog.com/Khan/archive/2024/04/30/230338.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>解析 ipa 文件版本号等信息(基于 python)</title><link>http://www.cppblog.com/Khan/archive/2015/01/04/209386.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Sun, 04 Jan 2015 05:10:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2015/01/04/209386.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/209386.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2015/01/04/209386.html#Feedback</comments><slash:comments>2</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/209386.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/209386.html</trackback:ping><description><![CDATA[python 3.x<br /><div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #008080; ">&nbsp;1</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">!/usr/bin/python</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;2</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;Filename:&nbsp;ipaInfo3.py</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;3</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;author&nbsp;khan.lau</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;4</span>&nbsp;<span style="color: #008000; "></span><br /><span style="color: #008080; ">&nbsp;5</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;python&nbsp;3.x</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;6</span>&nbsp;<span style="color: #008000; "></span><br /><span style="color: #008080; ">&nbsp;7</span>&nbsp;<span style="color: #0000FF; ">import</span>&nbsp;zipfile,&nbsp;plistlib,&nbsp;sys,&nbsp;re<br /><span style="color: #008080; ">&nbsp;8</span>&nbsp;<br /><span style="color: #008080; ">&nbsp;9</span>&nbsp;<br /><span style="color: #008080; ">10</span>&nbsp;<span style="color: #0000FF; ">def</span>&nbsp;analyze_ipa_with_plistlib(ipa_path):<br /><span style="color: #008080; ">11</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ipa_file&nbsp;=&nbsp;zipfile.ZipFile(ipa_path)<br /><span style="color: #008080; ">12</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;plist_path&nbsp;=&nbsp;find_plist_path(ipa_file)<br /><span style="color: #008080; ">13</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;plist_data&nbsp;=&nbsp;ipa_file.read(plist_path)<br /><span style="color: #008080; ">14</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;plist_root&nbsp;=&nbsp;plistlib.loads(plist_data)<br /><span style="color: #008080; ">15</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;print_ipa_info(plist_root)<br /><span style="color: #008080; ">16</span>&nbsp;<br /><span style="color: #008080; ">17</span>&nbsp;<span style="color: #0000FF; ">def</span>&nbsp;print_ipa_info(plist_root):<br /><span style="color: #008080; ">18</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">print</span>&nbsp;(<span style="color: #800000; ">'</span><span style="color: #800000; ">Display&nbsp;Name:&nbsp;%s</span><span style="color: #800000; ">'</span>&nbsp;%&nbsp;plist_root[<span style="color: #800000; ">'</span><span style="color: #800000; ">CFBundleName</span><span style="color: #800000; ">'</span>])<br /><span style="color: #008080; ">19</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">print</span>&nbsp;(<span style="color: #800000; ">'</span><span style="color: #800000; ">Bundle&nbsp;Identifier:&nbsp;%s</span><span style="color: #800000; ">'</span>&nbsp;%&nbsp;plist_root[<span style="color: #800000; ">'</span><span style="color: #800000; ">CFBundleIdentifier</span><span style="color: #800000; ">'</span>])<br /><span style="color: #008080; ">20</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">print</span>&nbsp;(<span style="color: #800000; ">'</span><span style="color: #800000; ">Version:&nbsp;%s</span><span style="color: #800000; ">'</span>&nbsp;%&nbsp;plist_root[<span style="color: #800000; ">'</span><span style="color: #800000; ">CFBundleShortVersionString</span><span style="color: #800000; ">'</span>])<br /><span style="color: #008080; ">21</span>&nbsp;<br /><span style="color: #008080; ">22</span>&nbsp;<span style="color: #0000FF; ">def</span>&nbsp;find_plist_path(zip_file):<br /><span style="color: #008080; ">23</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;name_list&nbsp;=&nbsp;zip_file.namelist()<br /><span style="color: #008080; ">24</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;print&nbsp;name_list</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">25</span>&nbsp;<span style="color: #008000; "></span>&nbsp;&nbsp;&nbsp;&nbsp;pattern&nbsp;=&nbsp;re.compile(r<span style="color: #800000; ">'</span><span style="color: #800000; ">Payload/[^/]*.app/Info.plist</span><span style="color: #800000; ">'</span>)<br /><span style="color: #008080; ">26</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">for</span>&nbsp;path&nbsp;<span style="color: #0000FF; ">in</span>&nbsp;name_list:<br /><span style="color: #008080; ">27</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;m&nbsp;=&nbsp;pattern.match(path)<br /><span style="color: #008080; ">28</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">if</span>&nbsp;m&nbsp;<span style="color: #0000FF; ">is</span>&nbsp;<span style="color: #0000FF; ">not</span>&nbsp;None:<br /><span style="color: #008080; ">29</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">return</span>&nbsp;m.group()<br /><span style="color: #008080; ">30</span>&nbsp;<br /><span style="color: #008080; ">31</span>&nbsp;<br /><span style="color: #008080; ">32</span>&nbsp;<br /><span style="color: #008080; ">33</span>&nbsp;<span style="color: #0000FF; ">if</span>&nbsp;<span style="color: #800080; ">__name__</span>&nbsp;==&nbsp;<span style="color: #800000; ">'</span><span style="color: #800000; ">__main__</span><span style="color: #800000; ">'</span>:<br /><span style="color: #008080; ">34</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;args&nbsp;=&nbsp;sys.argv[1:]<br /><span style="color: #008080; ">35</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">if</span>&nbsp;len(args)&nbsp;&lt;&nbsp;1:<br /><span style="color: #008080; ">36</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">print</span>&nbsp;(<span style="color: #800000; ">'</span><span style="color: #800000;">Usage:&nbsp;python ipaInfo3.py&nbsp;/path/to/ipa</span><span style="color: #800000; ">'</span>)<br /><span style="color: #008080; ">37</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;exit(0);<br /><span style="color: #008080; ">38</span>&nbsp;&nbsp;<br /><span style="color: #008080; ">39</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ipa_path&nbsp;=&nbsp;args[0]<br /><span style="color: #008080; ">40</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;analyze_ipa_with_plistlib(ipa_path)<br /><span style="color: #008080; ">41</span>&nbsp;</div><br /><br />python 2.7.x<br /><div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><span style="color: #008080; ">&nbsp;1</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">!/usr/bin/python</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;2</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;Filename:&nbsp;ipaInfo2.py</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;3</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;author&nbsp;khan.lau</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;4</span>&nbsp;<span style="color: #008000; "></span><br /><span style="color: #008080; ">&nbsp;5</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;python&nbsp;2.7.5</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;6</span>&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;project&nbsp;need&nbsp;third_party&nbsp;lib&nbsp;biplist,&nbsp;please&nbsp;run&nbsp;'sudo&nbsp;pip&nbsp;install&nbsp;biplist'</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">&nbsp;7</span>&nbsp;<span style="color: #008000; "></span><br /><span style="color: #008080; ">&nbsp;8</span>&nbsp;<span style="color: #0000FF; ">import</span>&nbsp;zipfile,&nbsp;biplist,&nbsp;sys,&nbsp;re<br /><span style="color: #008080; ">&nbsp;9</span>&nbsp;<br /><span style="color: #008080; ">10</span>&nbsp;<br /><span style="color: #008080; ">11</span>&nbsp;<span style="color: #0000FF; ">def</span>&nbsp;analyze_ipa_with_plistlib(ipa_path):<br /><span style="color: #008080; ">12</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ipa_file&nbsp;=&nbsp;zipfile.ZipFile(ipa_path)<br /><span style="color: #008080; ">13</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;plist_path&nbsp;=&nbsp;find_plist_path(ipa_file)<br /><span style="color: #008080; ">14</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;plist_data&nbsp;=&nbsp;ipa_file.read(plist_path)<br /><span style="color: #008080; ">15</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;plist_root&nbsp;=&nbsp;biplist.readPlistFromString(plist_data)<br /><span style="color: #008080; ">16</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;print_ipa_info(plist_root)<br /><span style="color: #008080; ">17</span>&nbsp;<br /><span style="color: #008080; ">18</span>&nbsp;<span style="color: #0000FF; ">def</span>&nbsp;print_ipa_info(plist_root):<br /><span style="color: #008080; ">19</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">print</span>&nbsp;(<span style="color: #800000; ">'</span><span style="color: #800000; ">Display&nbsp;Name:&nbsp;%s</span><span style="color: #800000; ">'</span>&nbsp;%&nbsp;plist_root[<span style="color: #800000; ">'</span><span style="color: #800000; ">CFBundleName</span><span style="color: #800000; ">'</span>])<br /><span style="color: #008080; ">20</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">print</span>&nbsp;(<span style="color: #800000; ">'</span><span style="color: #800000; ">Bundle&nbsp;Identifier:&nbsp;%s</span><span style="color: #800000; ">'</span>&nbsp;%&nbsp;plist_root[<span style="color: #800000; ">'</span><span style="color: #800000; ">CFBundleIdentifier</span><span style="color: #800000; ">'</span>])<br /><span style="color: #008080; ">21</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">print</span>&nbsp;(<span style="color: #800000; ">'</span><span style="color: #800000; ">Version:&nbsp;%s</span><span style="color: #800000; ">'</span>&nbsp;%&nbsp;plist_root[<span style="color: #800000; ">'</span><span style="color: #800000; ">CFBundleShortVersionString</span><span style="color: #800000; ">'</span>])<br /><span style="color: #008080; ">22</span>&nbsp;<br /><span style="color: #008080; ">23</span>&nbsp;<span style="color: #0000FF; ">def</span>&nbsp;find_plist_path(zip_file):<br /><span style="color: #008080; ">24</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;name_list&nbsp;=&nbsp;zip_file.namelist()<br /><span style="color: #008080; ">25</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #008000; ">#</span><span style="color: #008000; ">&nbsp;print&nbsp;name_list</span><span style="color: #008000; "><br /></span><span style="color: #008080; ">26</span>&nbsp;<span style="color: #008000; "></span>&nbsp;&nbsp;&nbsp;&nbsp;pattern&nbsp;=&nbsp;re.compile(r<span style="color: #800000; ">'</span><span style="color: #800000; ">Payload/[^/]*.app/Info.plist</span><span style="color: #800000; ">'</span>)<br /><span style="color: #008080; ">27</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">for</span>&nbsp;path&nbsp;<span style="color: #0000FF; ">in</span>&nbsp;name_list:<br /><span style="color: #008080; ">28</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;m&nbsp;=&nbsp;pattern.match(path)<br /><span style="color: #008080; ">29</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">if</span>&nbsp;m&nbsp;<span style="color: #0000FF; ">is</span>&nbsp;<span style="color: #0000FF; ">not</span>&nbsp;None:<br /><span style="color: #008080; ">30</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">return</span>&nbsp;m.group()<br /><span style="color: #008080; ">31</span>&nbsp;<br /><span style="color: #008080; ">32</span>&nbsp;<br /><span style="color: #008080; ">33</span>&nbsp;<br /><span style="color: #008080; ">34</span>&nbsp;<span style="color: #0000FF; ">if</span>&nbsp;<span style="color: #800080; ">__name__</span>&nbsp;==&nbsp;<span style="color: #800000; ">'</span><span style="color: #800000; ">__main__</span><span style="color: #800000; ">'</span>:<br /><span style="color: #008080; ">35</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;args&nbsp;=&nbsp;sys.argv[1:]<br /><span style="color: #008080; ">36</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">if</span>&nbsp;len(args)&nbsp;&lt;&nbsp;1:<br /><span style="color: #008080; ">37</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #0000FF; ">print</span>&nbsp;(<span style="color: #800000; ">'</span><span style="color: #800000; ">Usage:&nbsp;python ipaInfo2</span><span style="color: #800000; ">.py&nbsp;/path/to/ipa</span><span style="color: #800000; ">'</span>)<br /><span style="color: #008080; ">38</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;exit(0);<br /><span style="color: #008080; ">39</span>&nbsp;&nbsp;<br /><span style="color: #008080; ">40</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;ipa_path&nbsp;=&nbsp;args[0]<br /><span style="color: #008080; ">41</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;analyze_ipa_with_plistlib(ipa_path)</div><br /><br />python2.7 不包含 plistlib, 所以需要引入第三方库 biplist, &nbsp;使用 easy_install 或 pip 安装库即可, biplist 支持 data 解析, 相对于 plistlib 而已, 只需改动极少代码, 所以采用他<br /><img src ="http://www.cppblog.com/Khan/aggbug/209386.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2015-01-04 13:10 <a href="http://www.cppblog.com/Khan/archive/2015/01/04/209386.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>使用UIAppearance协议自定义视图</title><link>http://www.cppblog.com/Khan/archive/2014/06/21/207361.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Sat, 21 Jun 2014 07:33:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2014/06/21/207361.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/207361.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2014/06/21/207361.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/207361.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/207361.html</trackback:ping><description><![CDATA[<p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">我们再介绍一个对iOS 5的重要补充功能：通过苹果原生类库自定义视图外观。在iOS 5以前，自定义原生控件的外观并没有原生支持，因此开发人员感觉很麻烦。开发人员经常面临的问题是修改一个控件所有实例的外观。解决这个问题的正确方法是重写一遍控件。但由于这么做非常费时，一些开发人员开始覆盖或混写一些方法，如<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">drawRect:</code>。</p><p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">从iOS 5开始，苹果通过两个协议（<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIAppearance</code>和<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIAppearanceContainer</code>）规范了对许多UIKit控件定制的支持。所有遵循<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIAppearance</code>协议的UI控件通过定制都可以呈现各种外观。不仅如此，<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIAppearance</code>协议甚至允许开发者基于控件所属的区域指定不同的外观。也就是说，当某个控件包含在特定视图中时，可以指定它的外观（如<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIBarButtonItem</code>的<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">tintColor</code>）。也可以获取该控件类的外观代理对象，用该代理定制外观来实现，下面来看一个例子。</p><p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">要定制应用中所有条形按钮的颜色，可以在<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIBarButtonItem</code>的外观代理中设置<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">tintColor</code>：</p><pre style="padding: 8.5px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #333333; border-top-left-radius: 4px; border-top-right-radius: 4px; border-bottom-right-radius: 4px; border-bottom-left-radius: 4px; margin-top: 0px; margin-bottom: 18px; line-height: 18px; word-break: break-all; word-wrap: break-word; white-space: pre-wrap; border: 1px solid rgba(0, 0, 0, 0.14902); background-color: #f5f5f5;"><code style="padding: 0px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; color: inherit; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 0px; background-color: transparent;"><span style="color: #000000;">[[</span><span style="color: #2b91af;">UIBarButtonItem</span><span style="color: #000000;">  appearance</span><span style="color: #000000;">]</span><span style="color: #000000;">  setTintColor</span><span style="color: #000000;">:[</span><span style="color: #2b91af;">UIColor</span><span style="color: #000000;">  redColor</span><span style="color: #000000;">]];</span></code></pre><p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">注意，iOS 4的时候<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">setTintColor</code>方法就在<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIBarButtonItem</code>中了，但它只会作用到某个特定的控件实例，而不是所有的此类控件。借助外观代理对象，我们可以定制使用上述类创建的任意对象的外观。</p><p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">同样，可以根据内部包含的视图采用如下方法来定制控件的外观：</p><pre style="padding: 8.5px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #333333; border-top-left-radius: 4px; border-top-right-radius: 4px; border-bottom-right-radius: 4px; border-bottom-left-radius: 4px; margin-top: 0px; margin-bottom: 18px; line-height: 18px; word-break: break-all; word-wrap: break-word; white-space: pre-wrap; border: 1px solid rgba(0, 0, 0, 0.14902); background-color: #f5f5f5;"><code style="padding: 0px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; color: inherit; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 0px; background-color: transparent;"><span style="color: #000000;">[[</span><span style="color: #2b91af;">UIBarButtonItem</span><span style="color: #000000;"> appearanceWhenContainedIn</span><span style="color: #000000;">:[</span><span style="color: #2b91af;">UINavigationBar</span> <span style="color: #00008b;">class</span><span style="color: #000000;">],</span> <span style="color: #00008b;">nil</span><span style="color: #000000;">]</span><span style="color: #000000;">  setTintColor</span><span style="color: #000000;">:[</span><span style="color: #2b91af;">UIColor</span><span style="color: #000000;"> redColor</span><span style="color: #000000;">]];</span></code></pre><p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">第一个参数是以<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">nil</code>结尾的所有容器类的列表，包括<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UINavigatorBar</code>、<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIPopOverController</code>等遵循<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIAppearanceContainer</code>协议的类。</p><p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">从iOS 5开始，大多数UI元素都增加了对<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIAppearance</code>协议的支持。此外，iOS 5中类似于<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UISwitch</code>的控件允许我们方便地将on开关的颜色变成设计师选定的颜色。现在，怎么确定哪些情况下能够通过UIKit的外观代理来定制所有元素（以及元素中的哪些属性）呢？有两种方式。老办法是查阅文档，另一个办法是大多数开发人员使用的快捷方式：读头文件。打开对应的UIKit元素的头文件，其中所有带有<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UI_APPEARANCE_SELECTOR</code>标记的属性都支持通过外观代理来定制。举个例子，UINavigationBar.h中的<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">tintColor</code>属性带有<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UI_APPEARANCE_SELECTOR</code>标记：</p><pre style="padding: 8.5px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #333333; border-top-left-radius: 4px; border-top-right-radius: 4px; border-bottom-right-radius: 4px; border-bottom-left-radius: 4px; margin-top: 0px; margin-bottom: 18px; line-height: 18px; word-break: break-all; word-wrap: break-word; white-space: pre-wrap; border: 1px solid rgba(0, 0, 0, 0.14902); background-color: #f5f5f5;"><code style="padding: 0px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; color: inherit; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 0px; background-color: transparent;"><span style="color: #800000;">@property</span><span style="color: #000000;">(</span><span style="color: #000000;">nonatomic</span><span style="color: #000000;">,</span><span style="color: #000000;">retain</span><span style="color: #000000;">)</span> <span style="color: #2b91af;">UIColor</span> <span style="color: #000000;">*</span><span style="color: #000000;">tintColor    UI_APPEARANCE_SELECTOR</span><span style="color: #000000;">;</span></code></pre><p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">意味着可以调用</p><pre style="padding: 8.5px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #333333; border-top-left-radius: 4px; border-top-right-radius: 4px; border-bottom-right-radius: 4px; border-bottom-left-radius: 4px; margin-top: 0px; margin-bottom: 18px; line-height: 18px; word-break: break-all; word-wrap: break-word; white-space: pre-wrap; border: 1px solid rgba(0, 0, 0, 0.14902); background-color: #f5f5f5;"><code style="padding: 0px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; color: inherit; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 0px; background-color: transparent;"><span style="color: #000000;">[[</span><span style="color: #2b91af;">UINavigationBar</span><span style="color: #000000;">   appearance</span><span style="color: #000000;">]</span><span style="color: #000000;">  setTintColor</span><span style="color: #000000;">:</span><span style="color: #000000;">newColor</span><span style="color: #000000;">];</span></code></pre><p style="margin: 1em 0px; font-family: Verdana, Arial, Tahoma, Helvetica, Georgia, sans-serif, STXihei, 华文黑体, Hei, 'Hiragino Kaku Gothic Pro', SimSun; line-height: 23.799999237060547px; color: #333333; background-color: #ffffff;">尽管一开始苹果反对（在Mac和iOS平台上）使用UI定制，但情况慢慢发生了变化。苹果自己的原生应用（比如新的Reminder应用）也有了深度定制的、模仿现实的用户界面。有了<code style="padding: 2px 4px; font-family: Menlo, Monaco, Consolas, 'Courier New', monospace; font-size: 12px; color: #dd1144; border-top-left-radius: 3px; border-top-right-radius: 3px; border-bottom-right-radius: 3px; border-bottom-left-radius: 3px; border: 1px solid #e1e1e8; background-color: #f7f7f9;">UIAppearance</code>协议，实现同样效果所用的代码要少得多。</p><img src ="http://www.cppblog.com/Khan/aggbug/207361.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2014-06-21 15:33 <a href="http://www.cppblog.com/Khan/archive/2014/06/21/207361.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>XMPP概览</title><link>http://www.cppblog.com/Khan/archive/2013/08/01/202275.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 01 Aug 2013 05:43:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2013/08/01/202275.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/202275.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2013/08/01/202275.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/202275.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/202275.html</trackback:ping><description><![CDATA[<div>XMPP-framework实现部分 , <span style="color: red;">(x)标注为尚未实现部分
</span><div><br />
RFC3920 &nbsp; Core<span style="white-space: pre;">&nbsp;</span>核心协议 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;http://wiki.jabbercn.org/RFC3920<br />
RFC3921 &nbsp; IM<span style="white-space: pre;">&nbsp;</span>即时信息 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; http://wiki.jabbercn.org/RFC3921<br />
<br />
</div>
<div>XEP-0009 &nbsp;Jabber-RPC&nbsp;在两个XMPP实体间传输XML-RPC编码请求和响应<br />
XEP-0012 &nbsp;Last Activity<span style="white-space: pre;">&nbsp;</span>最后活动<span style="color: red;"> (x)</span> &nbsp; &nbsp; &nbsp;&nbsp;</div>
<div>XEP-0016 &nbsp;隐私列表 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;http://wiki.jabbercn.org/XEP-0016<br />
XEP-0030 &nbsp;Service Discovery<span style="white-space: pre;">&nbsp;</span>服务发现<span style="color: red;"> (x) </span>&nbsp; &nbsp; &nbsp; http://wiki.jabbercn.org/XEP-0030</div>
<div>XEP-0045 &nbsp;多用户聊天 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; http://wiki.jabbercn.org/XEP-0045<br />
XEP-0047 &nbsp;In-Band Bytestreams<span style="white-space: pre;">&nbsp; </span>带内字节流 <span style="color: red;">(x)</span><br />
<div>XEP-0048 &nbsp;Bookmarks<span style="white-space: pre;">&nbsp;</span>书签<span style="color: red;"> &nbsp;(x)</span></div>
<div>XEP-0049 &nbsp;Private XML Storage<span style="white-space: pre;">&nbsp;</span>私有XML存储<span style="color: red;"> (x)</span></div>
</div>
<div>XEP-0054 &nbsp;电子名片 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;http://wiki.jabbercn.org/XEP-0054<br />
XEP-0055 &nbsp;Jabber Search<span style="white-space: pre;">&nbsp;</span>Jabber搜索&nbsp;<span style="color: red;">(x)</span></div>
<div>XEP-0060 &nbsp;发布 订阅 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; http://wiki.jabbercn.org/XEP-0060</div>
<div>XEP-0065 &nbsp;SOCKS5字节流,&nbsp;两个XMPP用户之间建立一个带外流，主要用于文件传输 &nbsp;<span style="font-family: sans-serif; font-size: 13px; line-height: 19px; background-color: #ffffff;"></span>http://wiki.jabbercn.org/XEP-0065<br />
XEP-0066 &nbsp;Out of Band Data<span style="white-space: pre;">&nbsp;</span>带外数据 <span style="color: red;">&nbsp;(x)</span><br />
XEP-0071 &nbsp;XHTML-IM<span style="white-space: pre;">&nbsp;</span>xhtml即时消息 &nbsp; &nbsp; <span style="color: red;">(x)</span><br />
<div>XEP-0077 &nbsp;In-Band Registration 带内注册 &nbsp;<span style="color: red;">(x)</span> &nbsp;http://wiki.jabbercn.org/XEP-0077</div>
</div>
<div>XEP-0082 &nbsp;日期和时间信息的标准化表示&nbsp;</div>
<div>XEP-0085 &nbsp;聊天状态通知,&nbsp;聊天对话中通知用户状态 &nbsp;http://wiki.jabbercn.org/XEP-0085<br />
<div>XEP-0092 &nbsp;Software Version 软件版本 &nbsp;<span style="color: red;">(x)</span><br />
<div>XEP-0096 &nbsp;SI File Transfer 文件传输的流初始化<span style="color: red;"> (x) </span>&nbsp;http://wiki.jabbercn.org/XEP-0096</div>
</div>
</div>
XEP-0100 &nbsp;网关交互,表述了XMPP客户端与提供传统的IM服务的代理网关之间交换的最佳实践 &nbsp;&nbsp;http://wiki.jabbercn.org/XEP-0100<br />XEP-0106<span style="white-space: pre;">&nbsp; </span>JID Escaping<br /><div>XEP-0115 &nbsp;Entity Capabilities 实体能力 <font color="#ff0000">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp;&nbsp;</font>&nbsp;http://wiki.jabbercn.org/XEP-0115</div><div>XEP-0128 &nbsp;Service Discovery Extensions 服务发现扩展<span style="color: red;"> (x)</span> &nbsp;http://wiki.jabbercn.org/XEP-0128<br />XEP-0136<span style="white-space: pre;">&nbsp; </span>Message Archiving</div><div>XEP-0153 &nbsp;vCard-Based Avatars 基于电子名片的头像<font color="#ff0000">&nbsp;&nbsp;</font>&nbsp;http://wiki.jabbercn.org/XEP-0153</div><div>XEP-0166 &nbsp;Jingle <span style="color: red;">(x)</span></div><div>XEP-0167 &nbsp;Jingle RTP Sessions jingle的RTP会话<font color="#ff0000"> (x)</font><br />XEP-0172<span style="white-space: pre;">&nbsp; </span>User Nickname</div><div>XEP-0176 &nbsp;Jingle ICE-UDP Transport Method &nbsp;jingle的ICE-UDp传输方法 <span style="color: red;">(x)</span></div><div>XEP-0177 &nbsp;Jingle Raw UDP Transport Method<font color="#ff0000"> (x)</font><br />XEP-0184<span style="white-space: pre;">&nbsp; </span>Message Delivery Receipts</div><div>XEP-0199 &nbsp;XMPP Ping</div><div>XEP-0202 &nbsp;Entity Time &nbsp;实体时间<br /><div>XEP-0203 &nbsp;Delayed Delivery<br /><div>XEP-0223 &nbsp;Persistent Storage of Private Data via PubSub<br /><div>XEP-0224 &nbsp;Attention</div></div></div></div><div>XEP-0234 &nbsp;Jingle File Transfer jingle文件传输 <span style="color: red;">(x)</span></div><div>XEP-0249 &nbsp;Direct MUC Invitation 直接邀请加入MUC群聊<font color="#ff0000"> (x)</font><br />XEP-0297<span style="white-space: pre;">&nbsp; </span>Stanza Forwarding</div><div>XEP-0308 &nbsp;Last Message Correction</div><br /><br />
</div><img src ="http://www.cppblog.com/Khan/aggbug/202275.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2013-08-01 13:43 <a href="http://www.cppblog.com/Khan/archive/2013/08/01/202275.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>视频流相关名词介绍</title><link>http://www.cppblog.com/Khan/archive/2013/03/24/198787.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Sun, 24 Mar 2013 13:56:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2013/03/24/198787.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/198787.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2013/03/24/198787.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/198787.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/198787.html</trackback:ping><description><![CDATA[<div>I frame ：帧内编码帧 又称intra picture，I 帧通常是每个 GOP（MPEG 所使用的一种视频压缩技术）的第一个帧，经过适度地压缩，做为随机访问的参考点，可以当成图象。I帧可以看成是一个图像经过压缩后的产物。</div><div></div><div>P frame: 前向预测编码帧 又称predictive-frame，通过充分将低于图像序列中前面已编码帧的时间冗余信息来压缩传输数据量的编码图像，也叫预测帧；</div><div></div><div>B frame: 双向预测内插编码帧 又称bi-directional interpolated prediction frame，既考虑与源图像序列前面已编码帧，也顾及源图像序列后面已编码帧之间的时间冗余信息来压缩传输数据量的编码图像，也叫双向预测帧；<br /></div><div></div><div>DTS Decode Time Stamp（解码时间戳）DTS主要是标识读入内存中的bit流在什么时候开始送入解码器中进行解码。</div><div></div><div>PTS Presentation Time Stamp（显示时间戳）PTS主要用于度量解码后的视频帧什么时候被显示出来<br /><br /></div><div></div><div>&nbsp; &nbsp; DTS和PTS分别是解码器进行解码和显示帧时相对于SCR（系统参考）的时间戳。SCR可以理解为解码器应该开始从磁盘读取数据时的时间。</div><div></div><div>&nbsp; &nbsp; mpeg文件中的每一个包都有一个SCR时间戳并且这个时间戳就是读取这个数据包时的系统时间。通常情况下，解码器会在它开始读取mpeg流时启动系统时钟（系统时钟的初始值是第一个数据包的SCR值，通常为0但也可以不从0开始）。</div><div></div><div>&nbsp; &nbsp; DTS 时间戳决定了解码器在SCR时间等于DTS时间时进行解码，PTS时间戳也是类似的。通常，DTS/PTS时间戳指示的是晚于音视频包中的SCR的一个时 间。例如，如果一个视频数据包的SCR是100ms（意味着此包是播放100ms以后从磁盘中读取的），那么DTS/PTS值就差不多是200 /280ms，表明当SCR到200ms时这个视频数据应该被解码并在80ms以后被显示出来（视频数据在一个buffer中一直保存到开始解码）</div><div>&nbsp; &nbsp; 下溢通常发生在设置的视频数据流相关mux率太高。如果mux率是1000000bits/sec（意味着解码器要以1000000bits/sec的速率 读取文件），可是视频速率是2000000bits/sec（意味着需要以2000000bits/sec的速率显示视频数据），从磁盘中读取视频数据时 速度不够快以至于1秒钟内不能够读取足够的视频数据。这种情况下DTS/PTS时间戳就会指示视频在从硬盘中读出来之前进行解码或显示（DTS/PTS时间戳就要比包含它们的数据包中的SCR时间要早了）。</div><div>&nbsp; &nbsp; 如今依靠解码器，着基本已经不是什么问题了（尽管MPEG文件因为应该没有下溢而并不完全符合MPEG标准）。一些解码器（很多著名的基于PC的播放器）尽可能快的读取文件以便显示视频，可以的话直接忽略SCR。</div><div>&nbsp; &nbsp; 注意在你提供的列表中，平均的视频流速率为～3Mbps（3000000bits/sec）但是它的峰值达到了14Mbps（相当大，DVD限制在 9.8Mbps内）。这意味着mux率需要调整足够大以处理14Mbps的部分， bbMPEG计算出来的mux率有时候太低而导致下溢。</div><div>&nbsp; &nbsp; 你计划让视频流速率这么高么？这已经超过了DVD的说明了，而且很可能在大多数独立播放其中都不能播放。如果你不是这么计划，我会从1增加mquant的值并且在视频设置中将最大码流设置为9Mbps以保持一个小一点的码流。</div><div>&nbsp; &nbsp; 如果你确实想让视频码率那么高，你需要增大mux率。从提供的列表可以得出bbMPEG使用14706800bits/sec或者1838350bytes /sec的mux率（总数据速率为：1838350bytes/sec（14706800bits/sec）行）。你在强制mux率字段设置的值应该是以 bytes/sec为单位并被50整除。所以我会从36767（1838350/50）开始，一直增加直到不会再出现下溢错误为止.<br /></div><div></div><div></div><div>在没有B帧存在的情况下DTS的顺序和PTS的顺序应该是一样的。<br /></div><div></div><div>I P B帧的不同：</div><div></div><div>I frame:自身可以通过视频解压算法解压成一张单独的完整的图片。</div><div></div><div>P frame：需要参考其前面的一个I frame 或者B frame来生成一张完整的图片。</div><div></div><div>B frame:则要参考其前一个I或者P帧及其后面的一个P帧来生成一张完整的图片。</div><div></div><div>两个I frame之间形成一个GOP，在x264中同时可以通过参数来设定bf的大小，即：I 和p或者两个P之间B的数量。</div><div></div><div>通过上述基本可以说明如果有B frame 存在的情况下一个GOP的最后一个frame一定是P.<br /></div><div></div><div>DTS和PTS的不同：</div><div></div><div>DTS主要用于视频的解码,在解码阶段使用.PTS主要用于视频的同步和输出.在display的时候使用.在没有B frame的情况下.DTS和PTS的输出顺序是一样的.<br /></div><div></div><div></div><div>例子:</div><div></div><div>下面给出一个GOP为15的例子,其解码的参照frame及其解码的顺序都在里面:<br /><br /><img src="http://www.cppblog.com/images/cppblog_com/khan/6584/o_201107272227028458.jpg" alt="" border="0" height="224" width="640" /></div><div></div><div></div><div></div><div>如上图：I frame 的解码不依赖于任何的其它的帧.而p frame的解码则依赖于其前面的I frame或者P frame.B frame的解码则依赖于其前的最近的一个I frame或者P frame 及其后的最近的一个P frame.<br /><br /><br /><br /><div>sample_rate<strong>&nbsp; 采样率</strong></div></div><div></div><img src ="http://www.cppblog.com/Khan/aggbug/198787.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2013-03-24 21:56 <a href="http://www.cppblog.com/Khan/archive/2013/03/24/198787.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>ffmpeg分析系列之七(打开输入的流)  </title><link>http://www.cppblog.com/Khan/archive/2012/12/14/196237.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 13 Dec 2012 17:47:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2012/12/14/196237.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/196237.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2012/12/14/196237.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/196237.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/196237.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: err&nbsp;=&nbsp;av_open_input_stream(ic_ptr,&nbsp;pb,&nbsp;filename,&nbsp;fmt,&nbsp;ap);                                                            int&nbsp;av_open_input_s...&nbsp;&nbsp;<a href='http://www.cppblog.com/Khan/archive/2012/12/14/196237.html'>阅读全文</a><img src ="http://www.cppblog.com/Khan/aggbug/196237.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2012-12-14 01:47 <a href="http://www.cppblog.com/Khan/archive/2012/12/14/196237.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>ffmpeg分析系列之四(探测输入的格式)</title><link>http://www.cppblog.com/Khan/archive/2012/12/14/196234.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 13 Dec 2012 17:32:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2012/12/14/196234.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/196234.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2012/12/14/196234.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/196234.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/196234.html</trackback:ping><description><![CDATA[<div>调用av_open_input_file(&amp;pFormatCtx, is-&gt;filename, NULL, 0, NULL)函数打开输入的文件.<br /><br /><br /></div><div></div><div>1. 分析一下函数原型:</div><div>int av_open_input_file(AVFormatContext **ic_ptr, // 输出参数: 格式上下文</div><div>&nbsp; &nbsp; const char *filename, // 文件名</div><div>&nbsp; &nbsp; AVInputFormat *fmt, // 输入的格式, 为NULL, 即未知</div><div>&nbsp; &nbsp; int buf_size, // 缓冲的大小, 为0</div><div>&nbsp; &nbsp; AVFormatParameters *ap); // 格式的参数, 为NULL<br /><br /><br /><br /></div><div></div><div>2. 初始化探测数据:</div><div>AVProbeData probe_data, *pd = &amp;probe_data;</div><div></div><div>pd-&gt;filename = "";</div><div>if (filename)</div><div>&nbsp; pd-&gt;filename = filename;</div><div>pd-&gt;buf = NULL;</div><div>pd-&gt;buf_size = 0;<br /><br /><br /><br /></div><div></div><div>3. 探测输入的格式:</div><div>if (!fmt) { // fmt == NULL, 成立</div><div>&nbsp; &nbsp; fmt = av_probe_input_format(pd, 0);</div><div>}<br /><br /><br /><br /></div><div></div><div>进入av_probe_input_format函数:</div><div>AVInputFormat *av_probe_input_format(AVProbeData *pd, int is_opened) {</div><div>&nbsp; &nbsp; int score=0;</div><div>&nbsp; &nbsp; return av_probe_input_format2(pd, is_opened, &amp;score);</div><div>}<br /><br /><br /><br /></div><div></div><div>进入av_probe_input_format2函数:</div><div>AVInputFormat *av_probe_input_format2(AVProbeData *pd, int is_opened, int *score_max)</div><div>{</div><div>&nbsp; &nbsp; AVInputFormat *fmt1, *fmt;</div><div>&nbsp; &nbsp; int score;</div><div></div><div>&nbsp; &nbsp; fmt = NULL;</div><div>&nbsp; &nbsp; for(fmt1 = first_iformat; fmt1 != NULL; fmt1 = fmt1-&gt;next) {</div><div>&nbsp; &nbsp; &nbsp; &nbsp; if (!is_opened == !(fmt1-&gt;flags &amp; AVFMT_NOFILE)) // is_opened == 0, fmt1-&gt;flags 没有设置 AVFMT_NOFILE 标志时成立</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; continue;&nbsp;</div><div>&nbsp; &nbsp; &nbsp; &nbsp; /* 省略部分代码 */</div><div>&nbsp; &nbsp; }<br /><br /><br /><br /><br /></div><div></div><div>见libavformat/raw.c文件:</div><div>AVInputFormat h264_demuxer = {</div><div>&nbsp; "h264",</div><div>&nbsp; NULL_IF_CONFIG_SMALL("raw H.264 video format"),</div><div>&nbsp; 0,</div><div>&nbsp; h264_probe,</div><div>&nbsp; video_read_header,</div><div>&nbsp; ff_raw_read_partial_packet,</div><div>&nbsp; .flags= AVFMT_GENERIC_INDEX,</div><div>&nbsp; .extensions = "h26l,h264,264", //FIXME remove after writing mpeg4_probe</div><div>&nbsp; .value = CODEC_ID_H264,</div><div>};<br /><br /><br /></div><div>由于 h264_demuxer.flags == AVFMT_GENERIC_INDEX, 所以上面成立, continue, 返回的 AVInputFormat 指针为 NULL, 探测不成功.</div><img src ="http://www.cppblog.com/Khan/aggbug/196234.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2012-12-14 01:32 <a href="http://www.cppblog.com/Khan/archive/2012/12/14/196234.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>ffmpeg分析系列之三(输入输出格式)</title><link>http://www.cppblog.com/Khan/archive/2012/12/14/196233.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 13 Dec 2012 17:24:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2012/12/14/196233.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/196233.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2012/12/14/196233.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/196233.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/196233.html</trackback:ping><description><![CDATA[<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><span style="font-size: 13px; line-height: 18px; text-align: justify; color: #454545; font-family: tahoma, helvetica, arial; ">(不知原始出处, 方便请告知, 此处转载于&nbsp;</span><span style="color: #aaaaaa; font-family: georgia, Verdana, Helvetica, Arial; font-size: 13px; line-height: 18px; text-align: justify; ">http://hi.baidu.com/monkeyifox</span><span style="font-size: 13px; line-height: 18px; text-align: justify; color: #454545; font-family: tahoma, helvetica, arial; ">)</span></div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><br />
</div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; ">探测数据结构:</div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><br />
</div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="color: #333333; font-family: Arial; font-size: 14px; line-height: 26px; text-align: left; border-collapse: collapse; ">
    <tbody>
        <tr style="font-size: 10pt; ">
            <td style="font-size: 10pt; ">
            <p style="margin-right: 5px; margin-left: 5px; font-size: 10pt; line-height: 19px; "><code><span style="color: #000000; "><span style="color: #ff9900; ">/** This structure contains the data a format has to probe a file. */</span><br style="font-size: 10pt; " />
            <span style="color: #00ff00; ">typedef</span>&nbsp;<span style="color: #00ff00; ">struct</span>&nbsp;AVProbeData&nbsp;<span style="color: #00cc00; ">{</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">const</span>&nbsp;<span style="color: #00ff00; ">char</span>&nbsp;<span style="color: #00cc00; ">*</span>filename<span style="color: #00cc00; ">;</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">unsigned</span>&nbsp;<span style="color: #00ff00; ">char</span>&nbsp;<span style="color: #00cc00; ">*</span>buf<span style="color: #00cc00; ">;</span>&nbsp;<span style="color: #ff9900; ">/**&lt; Buffer must have AVPROBE_PADDING_SIZE of extra allocated bytes filled with zero. */</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;buf_size<span style="color: #00cc00; ">;</span>&nbsp;<span style="color: #ff9900; ">/**&lt; Size of buf except extra allocated bytes */</span><br style="font-size: 10pt; " />
            <span style="color: #00cc00; ">}</span>&nbsp;AVProbeData<span style="color: #00cc00; ">;</span></span></code></p>
            </td>
        </tr>
    </tbody>
</table>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><br />
</div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><span style="font-size: 16px; "><span style="font-size: 13px; ">h264的探测函数:</span></span></div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><span style="font-size: 16px; "><span style="font-size: 13px; "><br />
</span></span></div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="color: #333333; font-family: Arial; font-size: 14px; line-height: 26px; text-align: left; border-collapse: collapse; ">
    <tbody>
        <tr>
            <td>
            <p style="margin-right: 5px; margin-left: 5px; line-height: 21px; "><code><span style="color: #000000; "><span style="color: #00ff00; ">static</span>&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;h264_probe<span style="color: #00cc00; ">(</span>AVProbeData&nbsp;<span style="color: #00cc00; ">*</span>p<span style="color: #00cc00; ">)</span><br />
            <span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff0000; ">uint32_t</span>&nbsp;code<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">-</span>1<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;sps<span style="color: #00cc00; ">=</span>0<span style="color: #00cc00; ">,</span>&nbsp;pps<span style="color: #00cc00; ">=</span>0<span style="color: #00cc00; ">,</span>&nbsp;idr<span style="color: #00cc00; ">=</span>0<span style="color: #00cc00; ">,</span>&nbsp;res<span style="color: #00cc00; ">=</span>0<span style="color: #00cc00; ">,</span>&nbsp;sli<span style="color: #00cc00; ">=</span>0<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;i<span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">for</span><span style="color: #00cc00; ">(</span>i<span style="color: #00cc00; ">=</span>0<span style="color: #00cc00; ">;</span>&nbsp;i<span style="color: #00cc00; ">&lt;</span>p<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>buf_size<span style="color: #00cc00; ">;</span>&nbsp;i<span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;code&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">(</span>code<span style="color: #00cc00; ">&lt;</span><span style="color: #00cc00; ">&lt;</span>8<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">+</span>&nbsp;p<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>buf<span style="color: #00cc00; ">[</span>i<span style="color: #00cc00; ">]</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span>&nbsp;<span style="color: #00cc00; ">(</span><span style="color: #00cc00; ">(</span>code&nbsp;<span style="color: #00cc00; ">&amp;</span>&nbsp;0xffffff00<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span>&nbsp;0x100<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;ref_idc<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">(</span>code<span style="color: #00cc00; ">&gt;</span><span style="color: #00cc00; ">&gt;</span>5<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">&amp;</span>3<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;type&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;code&nbsp;<span style="color: #00cc00; ">&amp;</span>&nbsp;0x1F<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">static</span>&nbsp;<span style="color: #00ff00; ">const</span>&nbsp;<span style="color: #ff0000; ">int8_t</span>&nbsp;ref_zero<span style="color: #00cc00; ">[</span>32<span style="color: #00cc00; ">]</span><span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;0<span style="color: #00cc00; ">,</span>&nbsp;0<span style="color: #00cc00; ">,</span>&nbsp;0<span style="color: #00cc00; ">,</span>&nbsp;0<span style="color: #00cc00; ">,</span><span style="color: #00cc00; ">-</span>1<span style="color: #00cc00; ">,</span>&nbsp;1<span style="color: #00cc00; ">,</span><span style="color: #00cc00; ">-</span>1<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">-</span>1<span style="color: #00cc00; ">,</span>&nbsp;1<span style="color: #00cc00; ">,</span>&nbsp;1<span style="color: #00cc00; ">,</span>&nbsp;1<span style="color: #00cc00; ">,</span>&nbsp;1<span style="color: #00cc00; ">,</span><span style="color: #00cc00; ">-</span>1<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;0<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<span style="color: #00cc00; ">,</span>&nbsp;2<br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">}</span><span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span><span style="color: #00cc00; ">(</span>code&nbsp;<span style="color: #00cc00; ">&amp;</span>&nbsp;0x80<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #ff9900; ">//forbidden bit<br />
            </span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;0<span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span><span style="color: #00cc00; ">(</span>ref_zero<span style="color: #00cc00; ">[</span>type<span style="color: #00cc00; ">]</span>&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span>&nbsp;1&nbsp;<span style="color: #00cc00; ">&amp;</span><span style="color: #00cc00; ">&amp;</span>&nbsp;ref_idc<span style="color: #00cc00; ">)</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;0<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span><span style="color: #00cc00; ">(</span>ref_zero<span style="color: #00cc00; ">[</span>type<span style="color: #00cc00; ">]</span>&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">-</span>1&nbsp;<span style="color: #00cc00; ">&amp;</span><span style="color: #00cc00; ">&amp;</span>&nbsp;<span style="color: #00cc00; ">!</span>ref_idc<span style="color: #00cc00; ">)</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;0<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span><span style="color: #00cc00; ">(</span>ref_zero<span style="color: #00cc00; ">[</span>type<span style="color: #00cc00; ">]</span>&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span>&nbsp;2<span style="color: #00cc00; ">)</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;res<span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">switch</span><span style="color: #00cc00; ">(</span>type<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">case</span>&nbsp;1<span style="color: #00cc00; ">:</span>&nbsp;sli<span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">;</span>&nbsp;<span style="color: #00ff00; ">break</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">case</span>&nbsp;5<span style="color: #00cc00; ">:</span>&nbsp;idr<span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">;</span>&nbsp;<span style="color: #00ff00; ">break</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">case</span>&nbsp;7<span style="color: #00cc00; ">:</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span><span style="color: #00cc00; ">(</span>p<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>buf<span style="color: #00cc00; ">[</span>i<span style="color: #00cc00; ">+</span>2<span style="color: #00cc00; ">]</span><span style="color: #00cc00; ">&amp;</span>0x0F<span style="color: #00cc00; ">)</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;0<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sps<span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">break</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">case</span>&nbsp;8<span style="color: #00cc00; ">:</span>&nbsp;pps<span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">+</span><span style="color: #00cc00; ">;</span>&nbsp;<span style="color: #00ff00; ">break</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">}</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">}</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">}</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span><span style="color: #00cc00; ">(</span>sps&nbsp;<span style="color: #00cc00; ">&amp;</span><span style="color: #00cc00; ">&amp;</span>&nbsp;pps&nbsp;<span style="color: #00cc00; ">&amp;</span><span style="color: #00cc00; ">&amp;</span>&nbsp;<span style="color: #00cc00; ">(</span>idr<span style="color: #00cc00; ">|</span><span style="color: #00cc00; ">|</span>sli<span style="color: #00cc00; ">&gt;</span>3<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">&amp;</span><span style="color: #00cc00; ">&amp;</span>&nbsp;res<span style="color: #00cc00; ">&lt;</span><span style="color: #00cc00; ">(</span>sps<span style="color: #00cc00; ">+</span>pps<span style="color: #00cc00; ">+</span>idr<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">)</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;AVPROBE_SCORE_MAX<span style="color: #00cc00; ">/</span>2<span style="color: #00cc00; ">+</span>1<span style="color: #00cc00; ">;</span>&nbsp;<span style="color: #ff9900; ">// +1 for .mpg<br />
            </span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;0<span style="color: #00cc00; ">;</span><br />
            <span style="color: #00cc00; ">}</span><br />
            </span></code></p>
            </td>
        </tr>
    </tbody>
</table>
<br style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; " />
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><span style="font-size: 16px; "><span style="font-size: 13px; ">视频读首部函数:</span></span></div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><span style="font-size: 16px; "><span style="font-size: 13px; "><br />
</span></span></div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="color: #333333; font-family: Arial; font-size: 14px; line-height: 26px; text-align: left; border-collapse: collapse; ">
    <tbody>
        <tr>
            <td>
            <p style="margin-right: 5px; margin-left: 5px; line-height: 21px; "><code><span style="color: #000000; "><span style="color: #00ff00; ">static</span>&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;video_read_header<span style="color: #00cc00; ">(</span>AVFormatContext&nbsp;<span style="color: #00cc00; ">*</span>s<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;AVFormatParameters&nbsp;<span style="color: #00cc00; ">*</span>ap<span style="color: #00cc00; ">)</span><br />
            <span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;AVStream&nbsp;<span style="color: #00cc00; ">*</span>st<span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;st&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;av_new_stream<span style="color: #00cc00; ">(</span>s<span style="color: #00cc00; ">,</span>&nbsp;0<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span>&nbsp;<span style="color: #00cc00; ">(</span><span style="color: #00cc00; ">!</span>st<span style="color: #00cc00; ">)</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;AVERROR<span style="color: #00cc00; ">(</span>ENOMEM<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec_type&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;AVMEDIA_TYPE_VIDEO<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec_id&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;s<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>iformat<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>value<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>need_parsing&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;AVSTREAM_PARSE_FULL<span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff9900; ">/* for MJPEG, specify frame rate */</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff9900; ">/* for MPEG-4 specify it, too (most MPEG-4 streams do not have the fixed_vop_rate set ...)*/</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span>&nbsp;<span style="color: #00cc00; ">(</span>ap<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span><span style="color: #ff0000; ">time_base</span><span style="color: #00cc00; ">.</span>num<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span><span style="color: #ff0000; ">time_base</span><span style="color: #00cc00; ">=</span>&nbsp;ap<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span><span style="color: #ff0000; ">time_base</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">}</span>&nbsp;<span style="color: #00ff00; ">else</span>&nbsp;<span style="color: #00ff00; ">if</span>&nbsp;<span style="color: #00cc00; ">(</span>&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec_id&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span>&nbsp;CODEC_ID_MJPEG&nbsp;<span style="color: #00cc00; ">|</span><span style="color: #00cc00; ">|</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec_id&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span>&nbsp;CODEC_ID_MPEG4&nbsp;<span style="color: #00cc00; ">|</span><span style="color: #00cc00; ">|</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec_id&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span>&nbsp;CODEC_ID_DIRAC&nbsp;<span style="color: #00cc00; ">|</span><span style="color: #00cc00; ">|</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec_id&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span>&nbsp;CODEC_ID_DNXHD&nbsp;<span style="color: #00cc00; ">|</span><span style="color: #00cc00; ">|</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec_id&nbsp;<span style="color: #00cc00; ">=</span><span style="color: #00cc00; ">=</span>&nbsp;CODEC_ID_H264<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;st<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>codec<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span><span style="color: #ff0000; ">time_base</span><span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">(</span>AVRational<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">{</span>1<span style="color: #00cc00; ">,</span>25<span style="color: #00cc00; ">}</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">}</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;av_set_pts_info<span style="color: #00cc00; ">(</span>st<span style="color: #00cc00; ">,</span>&nbsp;64<span style="color: #00cc00; ">,</span>&nbsp;1<span style="color: #00cc00; ">,</span>&nbsp;1200000<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;0<span style="color: #00cc00; ">;</span><br />
            <span style="color: #00cc00; ">}</span></span></code></p>
            </td>
        </tr>
    </tbody>
</table>
<br style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; " />
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><span style="font-size: 16px; "><span style="font-size: 13px; ">原始地读实际的包函数:</span></span></div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><span style="font-size: 16px; "><span style="font-size: 13px; "><br />
</span></span></div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="color: #333333; font-family: Arial; font-size: 14px; line-height: 26px; text-align: left; border-collapse: collapse; ">
    <tbody>
        <tr>
            <td>
            <p style="margin-right: 5px; margin-left: 5px; line-height: 21px; "><code><span style="color: #000000; "><span style="color: #00ff00; ">int</span>&nbsp;ff_raw_read_partial_packet<span style="color: #00cc00; ">(</span>AVFormatContext&nbsp;<span style="color: #00cc00; ">*</span>s<span style="color: #00cc00; ">,</span>&nbsp;AVPacket&nbsp;<span style="color: #00cc00; ">*</span>pkt<span style="color: #00cc00; ">)</span><br />
            <span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;ret<span style="color: #00cc00; ">,</span>&nbsp;size<span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;size&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;RAW_PACKET_SIZE<span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span>&nbsp;<span style="color: #00cc00; ">(</span>av_new_packet<span style="color: #00cc00; ">(</span>pkt<span style="color: #00cc00; ">,</span>&nbsp;size<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">&lt;</span>&nbsp;0<span style="color: #00cc00; ">)</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;AVERROR<span style="color: #00cc00; ">(</span>ENOMEM<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br />
            <br />
            &nbsp;&nbsp;&nbsp;&nbsp;pkt<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>pos<span style="color: #00cc00; ">=</span>&nbsp;url_ftell<span style="color: #00cc00; ">(</span>s<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>pb<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;pkt<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>stream_index&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;0<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;ret&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;get_partial_buffer<span style="color: #00cc00; ">(</span>s<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>pb<span style="color: #00cc00; ">,</span>&nbsp;pkt<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>data<span style="color: #00cc00; ">,</span>&nbsp;size<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span>&nbsp;<span style="color: #00cc00; ">(</span>ret&nbsp;<span style="color: #00cc00; ">&lt;</span>&nbsp;0<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;av_free_packet<span style="color: #00cc00; ">(</span>pkt<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;ret<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">}</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;pkt<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>size&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;ret<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;ret<span style="color: #00cc00; ">;</span><br />
            <span style="color: #00cc00; ">}</span></span></code></p>
            </td>
        </tr>
    </tbody>
</table>
<br style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; " />
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; ">原始地写包函数:</div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; "><br />
</div>
<div style="color: #333333; font-family: Arial; line-height: 26px; text-align: left; background-color: #ffffff; ">
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="border-collapse: collapse; ">
    <tbody>
        <tr style="font-size: 10pt; ">
            <td style="font-size: 10pt; ">
            <p style="margin-right: 5px; margin-left: 5px; font-size: 10pt; line-height: 19px; "><code><span style="color: #00ff00; ">static</span>&nbsp;<span style="color: #00ff00; ">int</span>&nbsp;raw_write_packet<span style="color: #00cc00; ">(</span><span style="color: #00ff00; ">struct</span>&nbsp;AVFormatContext&nbsp;<span style="color: #00cc00; ">*</span>s<span style="color: #00cc00; ">,</span>&nbsp;AVPacket&nbsp;<span style="color: #00cc00; ">*</span>pkt<span style="color: #00cc00; ">)</span><br style="font-size: 10pt; " />
            <span style="color: #00cc00; ">{</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;put_buffer<span style="color: #00cc00; ">(</span>s<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>pb<span style="color: #00cc00; ">,</span>&nbsp;pkt<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>data<span style="color: #00cc00; ">,</span>&nbsp;pkt<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>size<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;put_flush_packet<span style="color: #00cc00; ">(</span>s<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>pb<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">return</span>&nbsp;0<span style="color: #00cc00; ">;</span><br style="font-size: 10pt; " />
            <span style="color: #00cc00; ">}</span></code></p>
            </td>
        </tr>
    </tbody>
</table>
<div><span style="font-size: 13px; "><br />
</span></div>
<div><span style="font-size: 13px; ">h264混合器:</span></div>
<div><span style="font-size: 13px; "><br />
</span></div>
<div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="border-collapse: collapse; ">
    <tbody>
        <tr style="font-size: 10pt; ">
            <td style="font-size: 10pt; ">
            <p style="margin-right: 5px; margin-left: 5px; font-size: 10pt; line-height: 19px; "><code>AVOutputFormat h264_muxer&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">{</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff0ff0; ">"h264"</span><span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;NULL_IF_CONFIG_SMALL<span style="color: #00cc00; ">(</span><span style="color: #ff0ff0; ">"raw H.264 video format"</span><span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff0000; ">NULL</span><span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff0ff0; ">"h264"</span><span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;0<span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;CODEC_ID_NONE<span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;CODEC_ID_H264<span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff0000; ">NULL</span><span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;raw_write_packet<span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">.</span>flags<span style="color: #00cc00; ">=</span>&nbsp;AVFMT_NOTIMESTAMPS<span style="color: #00cc00; ">,</span><br style="font-size: 10pt; " />
            <span style="color: #00cc00; ">}</span><span style="color: #00cc00; ">;</span></code></p>
            <div><code><span style="color: #00cc00; "><br />
            </span></code></div>
            </td>
        </tr>
    </tbody>
</table>
<div><span style="font-size: 16px; "><span style="font-size: 13px; "><br />
</span></span></div>
<div><span style="font-size: 16px; "><span style="font-size: 13px; ">h264分离器:</span></span></div>
<div><span style="font-size: 16px; "><span style="font-size: 13px; "><br />
</span></span></div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="border-collapse: collapse; ">
    <tbody>
        <tr>
            <td>
            <p style="margin-right: 5px; margin-left: 5px; line-height: 21px; "><code>AVInputFormat h264_demuxer&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff0ff0; ">"h264"</span><span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;NULL_IF_CONFIG_SMALL<span style="color: #00cc00; ">(</span><span style="color: #ff0ff0; ">"raw H.264 video format"</span><span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;0<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;h264_probe<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;video_read_header<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;ff_raw_read_partial_packet<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">.</span>flags<span style="color: #00cc00; ">=</span>&nbsp;AVFMT_GENERIC_INDEX<span style="color: #00cc00; ">,</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">.</span>extensions&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #ff0ff0; ">"h26l,h264,264"</span><span style="color: #00cc00; ">,</span>&nbsp;<span style="color: #ff9900; ">//FIXME remove after writing mpeg4_probe</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">.</span>value&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;CODEC_ID_H264<span style="color: #00cc00; ">,</span><br />
            <span style="color: #00cc00; ">}</span></code></p>
            </td>
        </tr>
    </tbody>
</table>
<br />
<div><span style="font-size: 16px; "><span style="font-size: 13px; ">libavformat/allformats.c文件的<span style="font-family: 新宋体; ">av_register_all函数</span>注册了h264分离器和混合器:</span></span></div>
<div><span style="font-size: 16px; "><span style="font-size: 13px; "><br />
</span></span></div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="border-collapse: collapse; ">
    <tbody>
        <tr>
            <td>
            <p style="margin-right: 5px; margin-left: 5px; line-height: 21px; "><code><span style="color: #00cc00; ">#</span><span style="color: #ff0000; ">define</span>&nbsp;REGISTER_MUXER<span style="color: #00cc00; ">(</span>X<span style="color: #00cc00; ">,</span>x<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">{</span>&nbsp;\<br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">extern</span>&nbsp;AVOutputFormat x<span style="color: #00cc00; ">#</span><span style="color: #00cc00; ">#</span>_muxer<span style="color: #00cc00; ">;</span>&nbsp;\<br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span><span style="color: #00cc00; ">(</span>CONFIG_<span style="color: #00cc00; ">#</span><span style="color: #00cc00; ">#</span>X<span style="color: #00cc00; ">#</span><span style="color: #00cc00; ">#</span>_MUXER<span style="color: #00cc00; ">)</span>&nbsp;av_register_output_format<span style="color: #00cc00; ">(</span><span style="color: #00cc00; ">&amp;</span>x<span style="color: #00cc00; ">#</span><span style="color: #00cc00; ">#</span>_muxer<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span>&nbsp;<span style="color: #00cc00; ">}</span><br />
            <br />
            <span style="color: #00cc00; ">#</span><span style="color: #ff0000; ">define</span>&nbsp;REGISTER_DEMUXER<span style="color: #00cc00; ">(</span>X<span style="color: #00cc00; ">,</span>x<span style="color: #00cc00; ">)</span>&nbsp;<span style="color: #00cc00; ">{</span>&nbsp;\<br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">extern</span>&nbsp;AVInputFormat x<span style="color: #00cc00; ">#</span><span style="color: #00cc00; ">#</span>_demuxer<span style="color: #00cc00; ">;</span>&nbsp;\<br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">if</span><span style="color: #00cc00; ">(</span>CONFIG_<span style="color: #00cc00; ">#</span><span style="color: #00cc00; ">#</span>X<span style="color: #00cc00; ">#</span><span style="color: #00cc00; ">#</span>_DEMUXER<span style="color: #00cc00; ">)</span>&nbsp;av_register_input_format<span style="color: #00cc00; ">(</span><span style="color: #00cc00; ">&amp;</span>x<span style="color: #00cc00; ">#</span><span style="color: #00cc00; ">#</span>_demuxer<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span>&nbsp;<span style="color: #00cc00; ">}</span><br />
            <br />
            <span style="color: #00cc00; ">#</span><span style="color: #ff0000; ">define</span>&nbsp;REGISTER_MUXDEMUX<span style="color: #00cc00; ">(</span>X<span style="color: #00cc00; ">,</span>x<span style="color: #00cc00; ">)</span>&nbsp;REGISTER_MUXER<span style="color: #00cc00; ">(</span>X<span style="color: #00cc00; ">,</span>x<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span>&nbsp;REGISTER_DEMUXER<span style="color: #00cc00; ">(</span>X<span style="color: #00cc00; ">,</span>x<span style="color: #00cc00; ">)</span></code></p>
            </td>
        </tr>
    </tbody>
</table>
<div><br />
</div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="border-collapse: collapse; ">
    <tbody>
        <tr>
            <td>
            <p style="margin-right: 5px; margin-left: 5px; line-height: 21px; "><code><span style="color: #00ff00; ">void</span>&nbsp;av_register_all<span style="color: #00cc00; ">(</span><span style="color: #00ff00; ">void</span><span style="color: #00cc00; ">)</span><br />
            <span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff9900; ">/* 省略部分代码 */</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff9900; ">/* protocols */</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;REGISTER_MUXDEMUX&nbsp;<span style="color: #00cc00; ">(</span>H264<span style="color: #00cc00; ">,</span>&nbsp;h264<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #ff9900; ">/* 省略部分代码 */</span><br />
            <span style="color: #00cc00; ">}</span></code></p>
            </td>
        </tr>
    </tbody>
</table>
<br />
<div><span style="font-size: 16px; "><span style="font-size: 13px; ">把注册格式函数也贴出来吧:</span></span></div>
<div><br />
</div>
</div>
<table cellpadding="0" cellspacing="0" width="95%" bgcolor="#f1f1f1" border="1" bordercolor="#999999" style="border-collapse: collapse; ">
    <tbody>
        <tr>
            <td>
            <p style="margin-right: 5px; margin-left: 5px; line-height: 21px; "><code><span style="color: #ff9900; ">/** head of registered input format linked list */</span><br />
            AVInputFormat&nbsp;<span style="color: #00cc00; ">*</span>first_iformat&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #ff0000; ">NULL</span><span style="color: #00cc00; ">;</span><br />
            <span style="color: #ff9900; ">/** head of registered output format linked list */</span><br />
            AVOutputFormat&nbsp;<span style="color: #00cc00; ">*</span>first_oformat&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #ff0000; ">NULL</span><span style="color: #00cc00; ">;</span></code></p>
            <p style="margin-right: 5px; margin-left: 5px; line-height: 21px; "><code><span style="color: #0000cc; "><br />
            </span><span style="color: #00ff00; ">void</span>&nbsp;av_register_input_format<span style="color: #00cc00; ">(</span>AVInputFormat&nbsp;<span style="color: #00cc00; ">*</span>format<span style="color: #00cc00; ">)</span><br />
            <span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;AVInputFormat&nbsp;<span style="color: #00cc00; ">*</span><span style="color: #00cc00; ">*</span>p<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;p&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">&amp;</span>first_iformat<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">while</span>&nbsp;<span style="color: #00cc00; ">(</span><span style="color: #00cc00; ">*</span>p&nbsp;<span style="color: #00cc00; ">!</span><span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #ff0000; ">NULL</span><span style="color: #00cc00; ">)</span>&nbsp;p&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">&amp;</span><span style="color: #00cc00; ">(</span><span style="color: #00cc00; ">*</span>p<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>next<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">*</span>p&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;format<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;format<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>next&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #ff0000; ">NULL</span><span style="color: #00cc00; ">;</span><br />
            <span style="color: #00cc00; ">}</span><br />
            <br />
            <span style="color: #00ff00; ">void</span>&nbsp;av_register_output_format<span style="color: #00cc00; ">(</span>AVOutputFormat&nbsp;<span style="color: #00cc00; ">*</span>format<span style="color: #00cc00; ">)</span><br />
            <span style="color: #00cc00; ">{</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;AVOutputFormat&nbsp;<span style="color: #00cc00; ">*</span><span style="color: #00cc00; ">*</span>p<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;p&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">&amp;</span>first_oformat<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00ff00; ">while</span>&nbsp;<span style="color: #00cc00; ">(</span><span style="color: #00cc00; ">*</span>p&nbsp;<span style="color: #00cc00; ">!</span><span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #ff0000; ">NULL</span><span style="color: #00cc00; ">)</span>&nbsp;p&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #00cc00; ">&amp;</span><span style="color: #00cc00; ">(</span><span style="color: #00cc00; ">*</span>p<span style="color: #00cc00; ">)</span><span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>next<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;<span style="color: #00cc00; ">*</span>p&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;format<span style="color: #00cc00; ">;</span><br />
            &nbsp;&nbsp;&nbsp;&nbsp;format<span style="color: #00cc00; ">-</span><span style="color: #00cc00; ">&gt;</span>next&nbsp;<span style="color: #00cc00; ">=</span>&nbsp;<span style="color: #ff0000; ">NULL</span><span style="color: #00cc00; ">;</span><br />
            <span style="color: #00cc00; ">}</span></code></p>
            </td>
        </tr>
    </tbody>
</table>
</div>
@import url(http://www.cppblog.com/cutesoft_client/cuteeditor/Load.ashx?type=style&file=SyntaxHighlighter.css);@import url(/css/cuteeditor.css);<img src ="http://www.cppblog.com/Khan/aggbug/196233.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2012-12-14 01:24 <a href="http://www.cppblog.com/Khan/archive/2012/12/14/196233.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>ffmpeg分析系列之二(文件协议)(转载)</title><link>http://www.cppblog.com/Khan/archive/2012/12/14/196232.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 13 Dec 2012 17:21:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2012/12/14/196232.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/196232.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2012/12/14/196232.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/196232.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/196232.html</trackback:ping><description><![CDATA[<div><span style="font-size: 13px; line-height: 18px; text-align: justify; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">(不知原始出处, 方便请告知, 此处转载于&nbsp;</span><span style="color: #aaaaaa; font-family: georgia, Verdana, Helvetica, Arial; font-size: 13px; line-height: 18px; text-align: justify; ">http://hi.baidu.com/monkeyifox</span><span style="font-size: 13px; line-height: 18px; text-align: justify; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">)</span></div>
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">
<div><span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><br />
</span></div>
URL协议结构:</span>
<p style="margin-right: 5px; margin-left: 5px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; line-height: 19px; font-size: 10pt; "><code>typedef struct URLProtocol {<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;const char *name;<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;int (*url_open)(URLContext *h, const char *url, int flags);<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;int (*url_read)(URLContext *h, unsigned char *buf, int size);<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;int (*url_write)(URLContext *h, unsigned char *buf, int size);<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;int64_t (*url_seek)(URLContext *h, int64_t pos, int whence);<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;int (*url_close)(URLContext *h);<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;struct URLProtocol *next;<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;int (*url_read_pause)(URLContext *h, int pause);<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;int64_t (*url_read_seek)(URLContext *h, int stream_index,<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;int64_t timestamp, int flags);<br style="font-size: 10pt; " />
&nbsp;&nbsp;&nbsp;&nbsp;int (*url_get_file_handle)(URLContext *h);<br style="font-size: 10pt; " />
} URLProtocol;</code></p>
<code style="color: #454545; background-color: #ffffff; "><br />
</code><span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "></span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">libavformat/file.c文件的file协议:</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>static int file_open(URLContext *h, const char *filename, int flags)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;int access;<br />
&nbsp;&nbsp;&nbsp;&nbsp;int fd;<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp; av_strstart(filename, "file:", &amp;filename);<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;if (flags &amp; URL_RDWR) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; access = O_CREAT | O_TRUNC | O_RDWR;<br />
&nbsp;&nbsp;&nbsp;&nbsp;} else if (flags &amp; URL_WRONLY) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; access = O_CREAT | O_TRUNC | O_WRONLY;<br />
&nbsp;&nbsp;&nbsp;&nbsp;} else {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; access = O_RDONLY;<br />
&nbsp;&nbsp;&nbsp;&nbsp;}<br />
#ifdef O_BINARY<br />
&nbsp;&nbsp;&nbsp;&nbsp; access |= O_BINARY;<br />
#endif<br />
&nbsp;&nbsp;&nbsp;&nbsp; fd = open(filename, access, 0666);<br />
&nbsp;&nbsp;&nbsp;&nbsp;if (fd == -1)<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return AVERROR(errno);<br />
&nbsp;&nbsp;&nbsp;&nbsp; h-&gt;priv_data = (void *) (intptr_t) fd;<br />
&nbsp;&nbsp;&nbsp;&nbsp;return 0;<br />
}<br />
<br />
static int file_read(URLContext *h, unsigned char *buf, int size)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;int fd = (intptr_t) h-&gt;priv_data;<br />
&nbsp;&nbsp;&nbsp;&nbsp;return read(fd, buf, size);<br />
}<br />
<br />
static int file_write(URLContext *h, unsigned char *buf, int size)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;int fd = (intptr_t) h-&gt;priv_data;<br />
&nbsp;&nbsp;&nbsp;&nbsp;return write(fd, buf, size);<br />
}<br />
<br />
/* XXX: use llseek */<br />
static int64_t file_seek(URLContext *h, int64_t pos, int whence)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;int fd = (intptr_t) h-&gt;priv_data;<br />
&nbsp;&nbsp;&nbsp;&nbsp;if (whence == AVSEEK_SIZE) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;struct stat st;<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;int ret = fstat(fd, &amp;st);<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return ret &lt; 0 ? AVERROR(errno) : st.st_size;<br />
&nbsp;&nbsp;&nbsp;&nbsp;}<br />
&nbsp;&nbsp;&nbsp;&nbsp;return lseek(fd, pos, whence);<br />
}<br />
<br />
static int file_close(URLContext *h)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;int fd = (intptr_t) h-&gt;priv_data;<br />
&nbsp;&nbsp;&nbsp;&nbsp;return close(fd);<br />
}<br />
<br />
static int file_get_handle(URLContext *h)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;return (intptr_t) h-&gt;priv_data;<br />
}<br />
<br />
URLProtocol file_protocol = {<br />
&nbsp;&nbsp;&nbsp;&nbsp;"file",<br />
&nbsp;&nbsp;&nbsp;&nbsp; file_open,<br />
&nbsp;&nbsp;&nbsp;&nbsp; file_read,<br />
&nbsp;&nbsp;&nbsp;&nbsp; file_write,<br />
&nbsp;&nbsp;&nbsp;&nbsp; file_seek,<br />
&nbsp;&nbsp;&nbsp;&nbsp; file_close,<br />
&nbsp;&nbsp;&nbsp;&nbsp;.url_get_file_handle = file_get_handle,<br />
};<br />
</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">libavformat/allformats.c文件的av_register_all函数注册了file协议:</span>
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>#define REGISTER_PROTOCOL(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;extern URLProtocol x##_protocol; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_PROTOCOL) av_register_protocol(&amp;x##_protocol); }</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>void av_register_all(void)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;/* 省略部分代码 */<br />
&nbsp;&nbsp;&nbsp;&nbsp;/* protocols */<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_PROTOCOL (FILE, file);<br />
&nbsp;&nbsp;&nbsp;&nbsp;/* 省略部分代码 */<br />
}</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">把注册协议函数也贴出来吧:</span>
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>URLProtocol *first_protocol = NULL;</code></p>
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code><br />
int av_register_protocol(URLProtocol *protocol)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp; URLProtocol **p;<br />
&nbsp;&nbsp;&nbsp;&nbsp; p = &amp;first_protocol;<br />
&nbsp;&nbsp;&nbsp;&nbsp;while (*p != NULL) p = &amp;(*p)-&gt;next;<br />
&nbsp;&nbsp;&nbsp;&nbsp;*p = protocol;<br />
&nbsp;&nbsp;&nbsp;&nbsp; protocol-&gt;next = NULL;<br />
&nbsp;&nbsp;&nbsp;&nbsp;return 0;<br />
}</code></p>
<img src ="http://www.cppblog.com/Khan/aggbug/196232.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2012-12-14 01:21 <a href="http://www.cppblog.com/Khan/archive/2012/12/14/196232.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>ffmpeg分析系列之一(注册该注册的)(转载)</title><link>http://www.cppblog.com/Khan/archive/2012/12/14/196231.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 13 Dec 2012 17:18:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2012/12/14/196231.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/196231.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2012/12/14/196231.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/196231.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/196231.html</trackback:ping><description><![CDATA[<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">&nbsp;(不知原始出处, 方便请告知, 此处转载于 </span>http://hi.baidu.com/monkeyifox<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">)</span>
<div><span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><br />
</span></div>
<div><span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">hello，各位好，本人是一名嵌入式软件工程师，目前正使用ffmpeg开发一款嵌入式多媒体播放器，《ffmpeg分析》系列博文是本人在阅读ffmpeg源代码时所做的笔记，希望对各位有点帮助。分析过程结合下面的例程：&nbsp;&nbsp;&nbsp;&nbsp;</span><a href="http://dranger.com/ffmpeg/tutorial05.c" style="color: #3fa7cb; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">http://dranger.com/ffmpeg/tutorial05.c</a><span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">&nbsp;一. 调用av_register_all函数注册所有的格式和编码解码器. 1.1 先调用avcodec_register_all函数注册所有的编码解码器. 1. 下面列出与H264相关的注册:</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>&nbsp;&nbsp; // 注册硬件加速器<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_HWACCEL (H264_DXVA2, h264_dxva2);<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_HWACCEL (H264_VAAPI, h264_vaapi);<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;// 注册解码器<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_DECODER (H264, h264);<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_DECODER (H264_VDPAU, h264_vdpau);<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;// 注册编码器<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_ENCODER (LIBX264, libx264);<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;// 注册分析器<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_PARSER (H264, h264);<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;// 注册位流分离器<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_BSF (H264_MP4TOANNEXB, h264_mp4toannexb);</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">2. 下面列出注册宏:</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>#define REGISTER_HWACCEL(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;extern AVHWAccel x##_hwaccel; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_HWACCEL) av_register_hwaccel(&amp;x##_hwaccel); }<br />
<br />
#define REGISTER_ENCODER(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;extern AVCodec x##_encoder; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_ENCODER) avcodec_register(&amp;x##_encoder); }<br />
<br />
#define REGISTER_DECODER(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;extern AVCodec x##_decoder; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_DECODER) avcodec_register(&amp;x##_decoder); }<br />
<br />
#define REGISTER_ENCDEC(X,x) REGISTER_ENCODER(X,x); REGISTER_DECODER(X,x)<br />
<br />
#define REGISTER_PARSER(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;extern AVCodecParser x##_parser; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_PARSER) av_register_codec_parser(&amp;x##_parser); }<br />
<br />
#define REGISTER_BSF(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;extern AVBitStreamFilter x##_bsf; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_BSF) av_register_bitstream_filter(&amp;x##_bsf); }</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">3. 分析一下注册函数, 以avcodec_register函数为例:</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>void avcodec_register(AVCodec *codec)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp; AVCodec **p;<br />
&nbsp;&nbsp;&nbsp;&nbsp; avcodec_init();<br />
&nbsp;&nbsp;&nbsp;&nbsp; p = &amp;first_avcodec;<br />
&nbsp;&nbsp;&nbsp;&nbsp;while (*p != NULL) p = &amp;(*p)-&gt;next;<br />
&nbsp;&nbsp;&nbsp;&nbsp;*p = codec;<br />
&nbsp;&nbsp;&nbsp;&nbsp; codec-&gt;next = NULL;<br />
}</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">&nbsp;&nbsp; 可以看到avcodec_register函数把输入的AVCodec连成一个链表, 其它注册函数与之类似, 就不多言了.</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">4. 上面调用了avcodec_init函数:</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>void avcodec_init(void)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;static int initialized = 0;<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;if (initialized != 0)<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;<br />
&nbsp;&nbsp;&nbsp;&nbsp; initialized = 1;<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp; dsputil_static_init ();<br />
}</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">&nbsp;&nbsp; 这个函数只会真正执行一次. 5. 上面调用了dsputil_static_init函数:</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>av_cold void dsputil_static_init(void)<br />
{<br />
&nbsp;&nbsp;&nbsp;&nbsp;int i;<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for(i=0;i&lt;256;i++) ff_cropTbl[i + MAX_NEG_CROP] = i;<br />
&nbsp;&nbsp;&nbsp;&nbsp;for(i=0;i&lt;MAX_NEG_CROP;i++) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ff_cropTbl[i] = 0;<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ff_cropTbl[i + MAX_NEG_CROP + 256] = 255;<br />
&nbsp;&nbsp;&nbsp;&nbsp;}<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for(i=0;i&lt;512;i++) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ff_squareTbl[i] = (i - 256) * (i - 256);<br />
&nbsp;&nbsp;&nbsp;&nbsp;}<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;for(i=0; i&lt;64; i++) inv_zigzag_direct16[ff_zigzag_direct[i]]= i+1;<br />
}</code></p>
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">&nbsp;&nbsp; &nbsp;&nbsp; 可以看到, 它初始化了一些静态数据. 1.2 注册所有的格式和外部库及协议.</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">1. 下面列出与H264相关的注册:</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>&nbsp;&nbsp; // 注册分离器和混合器<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_MUXDEMUX (H264, h264);<br />
<br />
&nbsp;&nbsp;&nbsp;&nbsp;// 注册文件协议<br />
&nbsp;&nbsp;&nbsp;&nbsp; REGISTER_PROTOCOL (FILE, file);</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">2. 下面列出注册宏:</span><br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<p style="margin: 0px; padding: 0px; color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; "><code>#define REGISTER_MUXER(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;extern AVOutputFormat x##_muxer; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_MUXER) av_register_output_format(&amp;x##_muxer); }<br />
<br />
#define REGISTER_DEMUXER(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;extern AVInputFormat x##_demuxer; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_DEMUXER) av_register_input_format(&amp;x##_demuxer); }<br />
<br />
#define REGISTER_MUXDEMUX(X,x) REGISTER_MUXER(X,x); REGISTER_DEMUXER(X,x)<br />
<br />
#define REGISTER_PROTOCOL(X,x) { \<br />
&nbsp;&nbsp;&nbsp;&nbsp;extern URLProtocol x##_protocol; \<br />
&nbsp;&nbsp;&nbsp;&nbsp;if(CONFIG_##X##_PROTOCOL) av_register_protocol(&amp;x##_protocol); }</code></p>
<br style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; " />
<span style="color: #454545; font-family: tahoma, helvetica, arial; background-color: #ffffff; ">&nbsp;&nbsp; 这些注册函数与avcodec_register函数类似, 就不多言了.</span>
@import url(http://www.cppblog.com/cutesoft_client/cuteeditor/Load.ashx?type=style&amp;file=SyntaxHighlighter.css);@import url(/css/cuteeditor.css);
</div><img src ="http://www.cppblog.com/Khan/aggbug/196231.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2012-12-14 01:18 <a href="http://www.cppblog.com/Khan/archive/2012/12/14/196231.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Daemon进程, shell也能搞定</title><link>http://www.cppblog.com/Khan/archive/2012/07/17/183827.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Mon, 16 Jul 2012 23:31:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2012/07/17/183827.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/183827.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2012/07/17/183827.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/183827.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/183827.html</trackback:ping><description><![CDATA[<div>more guard.sh&nbsp;</div><div>#!/bin/sh</div><div></div><div>while true; do</div><div></div><div>ps ax &gt; /tmp/ps.log</div><div></div><div>if grep 'h2es' /tmp/ps.log ; then</div><div>&nbsp; &nbsp; &nbsp; &nbsp; echo "Found h2es process!"</div><div>else</div><div>&nbsp; &nbsp; &nbsp; &nbsp; echo "Not found h2es process! Restart h2es"</div><div>&nbsp; &nbsp; &nbsp; &nbsp; cd /usr/local/hand2eye/server &amp;&amp; /usr/local/hand2eye/server/h2es</div><div>fi</div><div></div><div>sleep 10</div><div></div><div>done</div><img src ="http://www.cppblog.com/Khan/aggbug/183827.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2012-07-17 07:31 <a href="http://www.cppblog.com/Khan/archive/2012/07/17/183827.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>关于iphone accessory的理解</title><link>http://www.cppblog.com/Khan/archive/2011/10/09/157871.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Sun, 09 Oct 2011 06:47:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2011/10/09/157871.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/157871.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2011/10/09/157871.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/157871.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/157871.html</trackback:ping><description><![CDATA[转载自cocoachina&nbsp;<a href="http://www.cocoachina.com/">http://www.cocoachina.com<br /><br /></a><font class="Apple-style-span" face="Verdana" size="2"><div><div><span style="line-height: normal;">首先，如果我们的应用程序想跟外设传输数据，先要透过iphone的操作系统，也就是iphoneOS，而最开始的认证过程也是在外设和iphoneOS之间发生的，苹果为这个过程提供了一颗认证芯片(这颗芯片的作用是用来让iphoneOS识别这个外设是经过苹果公司承认的，他的通信方式是I2C总线，而且每出一个产品苹果都会收几美元的认证费用，苹果用心何其毒也~~~)</span></div><div><span style="line-height: normal;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; IphoneOS承认外设分两个步骤，识别和认证，我们先说说识别过程。</span></div><div><span style="line-height: normal;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; 识别过程是使用纯物理连接来实现的，在这个过程中iphone的30pin有三个引脚被用到，分别是Accessory Identify，Accessory Detect，Accessory Power，Accessory Identify接549k欧姆的电阻，告知iphoneOS使用串口通信，Accessory Detect直接接地，告知iphoneOS有外设插入，Accessory Power相当于iphoneOS的信号，待机时这个引脚没有输出，否则会有3.3V的电压输出。如果按照以上连接就完成了识别过程。</span></div><div><span style="line-height: normal;">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp;下面开始认证过程，认证过程也叫IDPS过程，这些就牵扯到苹果指定的通信协议了，苹果给自己的通信协议起了一个名字叫Lingo，Lingo分好多种有音频的lingo还有显示遥控的lingo，而我们认证使用的lingo叫做General Lingo。可能大家这时有点晕，那我就给大家看一个iphone的命令包。</span></div><div><span style="line-height: normal;">StartIDPS packet</span></div><div><span style="line-height: normal;">Byte &nbsp; &nbsp; Value &nbsp; &nbsp;Comment</span></div><div><span style="line-height: normal;">0 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;0XFF &nbsp; &nbsp;Sync byte（required only for UART serial）</span></div><div><span style="line-height: normal;">1 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;0X55 &nbsp; &nbsp;Start of packet(SOP)</span></div><div><span style="line-height: normal;">2 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;0XNN &nbsp; &nbsp;Length of packet payload</span></div><div><span style="line-height: normal;">3 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;0X00 &nbsp; &nbsp;General Lingo</span></div><div><span style="line-height: normal;">4 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;0X38 &nbsp; &nbsp;StartIDPS</span></div><div><span style="line-height: normal;">5 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;0XNN &nbsp; &nbsp;transID [bit 15:8] Transaction ID&nbsp;</span></div><div><span style="line-height: normal;">6 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;0XNN &nbsp; &nbsp;transID [bit 7:0]</span></div><div><span style="line-height: normal;">7 &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;0XNN &nbsp; &nbsp;校验</span></div><div><span style="line-height: normal;">这是iphone的命令包，大家看到这个应该就明白了。开始IDPS过程首先要发送StartIDPS命令，这样，外设与iphoneOS之间的认证过程就开始了。其中咱们应用中EAAccessory关于一些外设的属性，都是在这个过程中外设发给操作系统的，具体还是大家加入苹果的mfi(made for ipod)，拿到资料后，才能更明白。稍后我会将iphone串口通信的源码发出来。</span></div><div><span style="line-height: normal;"><br /></span></div><div><span style="line-height: normal;">MFI地址：http://developer.apple.com/programs/mfi/<br /><br /><br /><br />以下部分转载自&lt;iphone应用编程指南&gt;</span></div></div></font><span class="Apple-style-span" style="font-family: 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; font-size: 12px; line-height: normal; background-color: #ffffff; "><h2 class="jump section2" style="margin-top: 1.75em; font-size: 22px; color: #3c4c6c; padding-bottom: 2px; border-bottom-width: 1px; border-bottom-style: solid; border-bottom-color: #5088c5; ">和配件进行通讯</h2><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">在iPhone OS 3.0及之后的系统上，External Accessory<dfn class="pediaLink"><span class="pediaLink" data-header="框架" data-contents="框架是一个包含共享库及相关资源（比如nib文件、图像文件、和头文件）的程序包（即一个具有特定结构的目录）。" style="color: #3366cc; text-decoration: none; font-style: normal; border-bottom-width: 1px; border-bottom-style: dashed; border-bottom-color: #3366cc; white-space: nowrap; cursor: pointer; -webkit-transition-property: color, background-color, border-bottom, border-top-left-radius, border-top-right-radius, padding, margin; -webkit-transition-duration: 0.25s; "><a href="http://www.apple.com.cn/developer/iphone/library/documentation/General/Conceptual/DevPedia-CocoaCore/Framework.html#//apple_ref/doc/uid/TP40008195-CH56" target="_top" style="color: #3366cc; text-decoration: none; ">框架</a></span></dfn><code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">（ExternalAccessory.framework</code>）提供了一种管道机制，使应用程序可以和iPhone或iPod touch设备的配件进行通讯。通过这种管道，应用程序开发者可以将配件级别的功能集成到自己的程序中。</p><div class="notebox clear" style="clear: both; border-top-width: 1px; border-right-width: 1px; border-bottom-width: 1px; border-left-width: 1px; border-top-style: solid; border-right-style: solid; border-bottom-style: solid; border-left-style: solid; border-top-color: #5088c5; border-right-color: #5088c5; border-bottom-color: #5088c5; border-left-color: #5088c5; background-color: #ffffff; margin-top: 1.667em; margin-right: 0px; margin-bottom: 1.75em; margin-left: 0px; padding-right: 0.667em; padding-bottom: 0.083em; padding-left: 0.75em; text-align: left; "><p style="margin-top: 0.583em; margin-bottom: 0px; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; "><strong style="font-family: 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; font-size: 12px; font-weight: bold; ">请注意：</strong>下面部分将向您展示iPhone应用程序如何连接配件。如果您有兴趣成为iPhone或iPod touch配件的开发者，可以在<span class="content_text" style="margin-top: 0px; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; margin-bottom: 0.833em; padding-bottom: 0.833em; vertical-align: top; "><a href="http://developer.apple.com/" class="browserLink" style="color: #3366cc; text-decoration: none; ">http://developer.apple.com</a></span>网站上找到相应的信息。</p></div><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">为了使用External Accessory框架的接口，您必须将<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">ExternalAccessory.framework</code>加入到Xcode工程，并连接到相应的目标中。此外，还需要在相应的源代码文件的顶部包含一个<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">#import &lt;ExternalAccessory/ExternalAccessory.h&gt;</code>语句，才能访问该框架的类和头文件。有关如何为工程添加框架的更多信息，请参见<em><a href="http://developer.apple.com/iphone/library/documentation/DeveloperTools/Conceptual/XcodeProjectManagement/index.html#//apple_ref/doc/uid/TP40006917" target="_top" style="color: #3366cc; text-decoration: none; ">Xcode工程管理指南</a></em>中的<span class="content_text" style="margin-top: 0px; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; margin-bottom: 0.833em; padding-bottom: 0.833em; vertical-align: top; "><a href="http://developer.apple.com/iphone/library/documentation/DeveloperTools/Conceptual/XcodeProjectManagement/040-Files_in_Projects/project_files.html#//apple_ref/doc/uid/TP40002666" target="_top" style="color: #3366cc; text-decoration: none; ">工程中的文件</a></span>部分；有关External Accessory框架中类的一般信息，请参见<em><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/ExternalAccessoryFrameworkReference/index.html#//apple_ref/doc/uid/TP40008235" target="_top" style="color: #3366cc; text-decoration: none; ">External Accessory框架参考</a></em>。</p><br /><h3 class="jump section3" style="margin-top: 1.5em; margin-bottom: 0.25em; font-size: 17px; color: #000000; ">配件的基础</h3><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">在和配件进行通讯之前，需要与配件的制造商紧密合作，理解配件提供的服务。制造商必须在配件的硬件中加入显式的支持，才能和iPhone OS进行通讯。作为这种支持的一部分，配件必须支持至少一种命令<strong style="font-family: 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; font-size: 12px; font-weight: bold; ">协议</strong>，也就是支持一种定制的通讯模式，使配件和应用程序之间可以进行数据传输。苹果并不维护一个协议的注册表，支持何种协议及是否使用其他制造商支持的定制或标准协议是由制造商自行决定的。</p><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">作为和配件制造商通讯的一部分，您必须找出给定的配件支持什么协议。为了避免名字空间发生冲突，协议的名称由反向的DNS字符串来指定，形式是<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">com.apple.myProtocol</code>。这使得每个配件制造商都可以根据自己的需要定义协议，以支持不同的配件产品线。</p><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">应用程序通过打开一个使用指定协议的会话来和配件进行通讯。打开会话的方法是创建一个<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EASession_class/Reference/Reference.html#//apple_ref/occ/cl/EASession" target="_top" style="color: #3366cc; text-decoration: none; ">EASession</a></code>类的实例，该类中包含<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/Cocoa/Reference/Foundation/Classes/NSInputStream_Class/Reference/Reference.html#//apple_ref/occ/cl/NSInputStream" target="_top" style="color: #3366cc; text-decoration: none; ">NSInputStream</a></code>和<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/Cocoa/Reference/Foundation/Classes/NSOutputStream_Class/Reference/Reference.html#//apple_ref/occ/cl/NSOutputStream" target="_top" style="color: #3366cc; text-decoration: none; ">NSOutputStream</a></code>对象，可以和配件进行通讯。通过这些流对象，应用程序可以向配件发送未经加工的数据包，以及接收来自配件的类似数据包。因此，您必须按照期望的协议来理解每个数据包的格式。</p><a name="//apple_ref/doc/uid/TP40007072-CH14-SW26" title="Declaring the Protocols Your Application Supports" style="color: #3366cc; text-decoration: none; width: 20px; height: 20px; text-indent: 20px; background-image: url(http://www.cppblog.com/CuteSoft_Client/CuteEditor/Load.ashx?type=image&amp;file=anchor.gif); background-repeat: no-repeat no-repeat; "></a><h3 class="jump section3" style="margin-top: 1.5em; margin-bottom: 0.25em; font-size: 17px; color: #000000; ">声明应用程序支持的协议</h3><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">能够和配件通讯的应用程序应该在其<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">Info.plist</code>文件中声明支持的协议，使系统知道在相应的配件接入时，该应用程序可以被启动。如果当前没有应用程序可以支持接入的配件，系统可以选择启动App Store并指向支持该设备的应用程序。</p><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">为了声明支持的协议，您必须在应用程序的<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">Info.plist</code>文件中包含<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">UISupportedExternalAccessoryProtocols</code>键。该键包含一个字符串<dfn class="pediaLink"><span class="pediaLink" data-header="群体" data-contents="群体是Foundation框架中的一种对象，其主要作用是将对象存储为数组、字典、和集合。" style="color: #3366cc; text-decoration: none; font-style: normal; border-bottom-width: 1px; border-bottom-style: dashed; border-bottom-color: #3366cc; white-space: nowrap; cursor: pointer; -webkit-transition-property: color, background-color, border-bottom, border-top-left-radius, border-top-right-radius, padding, margin; -webkit-transition-duration: 0.25s; "><a href="http://www.apple.com.cn/developer/iphone/library/documentation/General/Conceptual/DevPedia-CocoaCore/Collection.html#//apple_ref/doc/uid/TP40008195-CH10" target="_top" style="color: #3366cc; text-decoration: none; ">数组</a></span></dfn>，用于标识应用程序支持的通讯协议。您的应用程序可以在这个列表中以任意顺序包含任意数量的协议。系统并不使用这个列表来确定应用程序应该选择哪个协议，而只是用它来确定应用程序是否能够和相应的配件进行通讯。您的代码需要在开始和配件进行对话时选择适当的通讯协议。</p><a name="//apple_ref/doc/uid/TP40007072-CH14-SW27" title="Connecting to an Accessory at Runtime" style="color: #3366cc; text-decoration: none; width: 20px; height: 20px; text-indent: 20px; background-image: url(http://www.cppblog.com/CuteSoft_Client/CuteEditor/Load.ashx?type=image&amp;file=anchor.gif); background-repeat: no-repeat no-repeat; "></a><h3 class="jump section3" style="margin-top: 1.5em; margin-bottom: 0.25em; font-size: 17px; color: #000000; ">在运行时连接配件</h3><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">在配件接入系统并做好通讯准备之前，通过External Accessory框架无法看到配件。当配件变为可见时，您的应用程序就可以获取相应的配件对象，然后用其支持的一或多个协议打开会话。</p><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">共享的<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EAAccessoryManager_class/Reference/Reference.html#//apple_ref/occ/cl/EAAccessoryManager" target="_top" style="color: #3366cc; text-decoration: none; ">EAAccessoryManager</a></code>对象为应用程序寻找与之通讯的配件提供主入口点。该类包含一个已经接入的配件对象的数组，您可以对其进行<dfn class="pediaLink"><span class="pediaLink" data-header="枚举" data-contents="枚举是顺序操作某个对象元素的过程&#8212;该对象通常是一个集合&#8212;每个元素最多操作一次，每次操作一个元素。" style="color: #3366cc; text-decoration: none; font-style: normal; border-bottom-width: 1px; border-bottom-style: dashed; border-bottom-color: #3366cc; white-space: nowrap; cursor: pointer; -webkit-transition-property: color, background-color, border-bottom, border-top-left-radius, border-top-right-radius, padding, margin; -webkit-transition-duration: 0.25s; "><a href="http://www.apple.com.cn/developer/iphone/library/documentation/General/Conceptual/DevPedia-CocoaCore/Enumeration.html#//apple_ref/doc/uid/TP40008195-CH17" target="_top" style="color: #3366cc; text-decoration: none; ">枚举</a></span></dfn>，看看是否存在应用程序支持的配件。<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EAAccessory_class/Reference/Reference.html#//apple_ref/occ/cl/EAAccessory" target="_top" style="color: #3366cc; text-decoration: none; ">EAAccessory</a></code>对象中的绝大多数信息（比如名称、制造商、和型号信息）都只是用于显示。如果您要确定应用程序是否可以连接一个配件，必须看配件的协议，确认应用程序是否支持其中的某个协议。</p><div class="notebox clear" style="clear: both; border-top-width: 1px; border-right-width: 1px; border-bottom-width: 1px; border-left-width: 1px; border-top-style: solid; border-right-style: solid; border-bottom-style: solid; border-left-style: solid; border-top-color: #5088c5; border-right-color: #5088c5; border-bottom-color: #5088c5; border-left-color: #5088c5; background-color: #ffffff; margin-top: 1.667em; margin-right: 0px; margin-bottom: 1.75em; margin-left: 0px; padding-right: 0.667em; padding-bottom: 0.083em; padding-left: 0.75em; text-align: left; "><p style="margin-top: 0.583em; margin-bottom: 0px; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; "><strong style="font-family: 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; font-size: 12px; font-weight: bold; ">请注意：</strong>多个配件对象支持同一协议是可能的。如果发生这种情况，您的代码必须负责选择使用哪个配件对象。</p></div><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">对于给定的配件对象，每次只能有一个指定协议的会话。<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">EAAccessory</code>对象的<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EAAccessory_class/Reference/Reference.html#//apple_ref/occ/instp/EAAccessory/protocolStrings" target="_top" style="color: #3366cc; text-decoration: none; ">protocolStrings</a></code>属性包含一个<dfn class="pediaLink"><span class="pediaLink" data-header="群体" data-contents="群体是Foundation框架中的一种对象，其主要作用是将对象存储为数组、字典、和集合。" style="color: #3366cc; text-decoration: none; font-style: normal; border-bottom-width: 1px; border-bottom-style: dashed; border-bottom-color: #3366cc; white-space: nowrap; cursor: pointer; -webkit-transition-property: color, background-color, border-bottom, border-top-left-radius, border-top-right-radius, padding, margin; -webkit-transition-duration: 0.25s; "><a href="http://www.apple.com.cn/developer/iphone/library/documentation/General/Conceptual/DevPedia-CocoaCore/Collection.html#//apple_ref/doc/uid/TP40008195-CH10" target="_top" style="color: #3366cc; text-decoration: none; ">字典</a></span></dfn>，字典的键是配件支持的协议。如果您试图用一个已经在使用的协议创建会话，External Accessory框架就会产生错误。</p><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; "><span class="content_text" style="margin-top: 0px; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; margin-bottom: 0.833em; padding-bottom: 0.833em; vertical-align: top; ">程序清单8-1</span>展示了如何检查接入配件的列表并从中取得应用程序支持的第一个配件。它为指定的协议创建一个会话，并对会话的输入和输出流进行配置。在这个方法返回会话对象时，已经完成和配件的连接，并可以开始发送和接收数据了。</p><br /><p class="codesample clear" style="margin-top: 1.667em; margin-bottom: -0.85em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; clear: both; "><strong style="font-family: 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; font-size: 12px; font-weight: bold; ">程序清单8-1&nbsp;&nbsp;</strong>创建和配件的通讯会话<br /><br /></p><div><div>- (EASession *)openSessionForProtocol:(NSString *)protocolString{</div><div>&nbsp; &nbsp; NSArray *accessories = [[EAAccessoryManager sharedAccessoryManager]</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;connectedAccessories];</div><div>&nbsp; &nbsp; EAAccessory *accessory = nil;</div><div>&nbsp; &nbsp; EASession *session = nil;</div><div>&nbsp;</div><div>&nbsp; &nbsp; for (EAAccessory *obj in accessories) {</div><div>&nbsp; &nbsp; &nbsp; &nbsp; if ([[obj protocolStrings] containsObject:protocolString]) {</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; accessory = obj;</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; break;</div><div>&nbsp; &nbsp; &nbsp; &nbsp; }</div><div>&nbsp; &nbsp; }</div><div>&nbsp;</div><div>&nbsp; &nbsp; if (accessory) {</div><div>&nbsp; &nbsp; &nbsp; &nbsp; session = [[EASession alloc] initWithAccessory:accessory</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;forProtocol:protocolString];</div><div>&nbsp; &nbsp; &nbsp; &nbsp; if (session) {</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; [[session inputStream] setDelegate:self];</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; [[session inputStream] scheduleInRunLoop:[NSRunLoop currentRunLoop]</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;forMode:NSDefaultRunLoopMode];</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; [[session inputStream] open];</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; [[session outputStream] setDelegate:self];</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; [[session outputStream] scheduleInRunLoop:[NSRunLoop currentRunLoop]</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;forMode:NSDefaultRunLoopMode];</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; [[session outputStream] open];</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; [session autorelease];</div><div>&nbsp; &nbsp; &nbsp; &nbsp; }</div><div>&nbsp; &nbsp; }</div><div>&nbsp; &nbsp; return session;</div><div>}</div></div><p>&nbsp;</p><div class="codesample clear" style="clear: both; font-size: 12px; margin-top: 1.5em; margin-right: 0px; margin-bottom: 1.5em; margin-left: 0px; "></div><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">在配置好输入输出流之后，最好一步就是处理和流相关的数据了。程序清单<span class="content_text" style="margin-top: 0px; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; margin-bottom: 0.833em; padding-bottom: 0.833em; vertical-align: top; ">8-2</span>展示了在<dfn class="pediaLink"><span class="pediaLink" data-header="委托" data-contents="委托是一种简单而强大的模式。在这种模式中，一个对象可以代表另一个对象进行动作或协调它的行为。" style="color: #3366cc; text-decoration: none; font-style: normal; border-bottom-width: 1px; border-bottom-style: dashed; border-bottom-color: #3366cc; white-space: nowrap; cursor: pointer; -webkit-transition-property: color, background-color, border-bottom, border-top-left-radius, border-top-right-radius, padding, margin; -webkit-transition-duration: 0.25s; "><a href="http://www.apple.com.cn/developer/iphone/library/documentation/General/Conceptual/DevPedia-CocoaCore/Delegation.html#//apple_ref/doc/uid/TP40008195-CH14" target="_top" style="color: #3366cc; text-decoration: none; ">委托</a></span></dfn>方法中处理流事件的基本代码结构。清单中的方法可以响应来自配件输入输出流的事件。当配件向应用程序发送数据时，事件发生表示有数据可供读取；类似地，当配件准备好接收应用程序数据时，也通过事件来表示（当然，您并不一定要等到这个事件发生才向流写出数据，应用程序也可以调用流的<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/Cocoa/Reference/Foundation/Classes/NSInputStream_Class/Reference/Reference.html#//apple_ref/occ/instm/NSInputStream/hasBytesAvailable" target="_top" style="color: #3366cc; text-decoration: none; ">hasBytesAvailable</a></code>方法来确认配件是否还能够接收数据）。有关流及如何处理流事件的更多信息，请参见<em><a href="http://developer.apple.com/iphone/library/documentation/Cocoa/Conceptual/Streams/index.html#//apple_ref/doc/uid/10000188i" target="_top" style="color: #3366cc; text-decoration: none; ">Cocoa流编程指南</a></em>。</p><br /><p class="codesample clear" style="margin-top: 1.667em; margin-bottom: -0.85em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; clear: both; "><strong style="font-family: 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; font-size: 12px; font-weight: bold; ">程序清单8-2&nbsp;&nbsp;</strong>处理流事件<br /><br /></p><div><div>// Handle communications from the streams.</div><div>- (void)stream:(NSStream*)theStream handleEvent:(NSStreamEvent)streamEvent{</div><div>&nbsp; &nbsp; switch (streamEvent){</div><div>&nbsp; &nbsp; &nbsp; &nbsp; case NSStreamHasBytesAvailable:</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; // Process the incoming stream data.</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; break;</div><div>&nbsp;</div><div>&nbsp; &nbsp; &nbsp; &nbsp; case NSStreamEventHasSpaceAvailable:</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; // Send the next queued command.</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; break;</div><div>&nbsp;</div><div>&nbsp; &nbsp; &nbsp; &nbsp; default:</div><div>&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; break;</div><div>&nbsp; &nbsp; }</div><div>}</div></div><p>&nbsp;</p><div class="codesample clear" style="clear: both; font-size: 12px; margin-top: 1.5em; margin-right: 0px; margin-bottom: 1.5em; margin-left: 0px; "></div><h3 class="jump section3" style="margin-top: 1.5em; margin-bottom: 0.25em; font-size: 17px; color: #000000; ">监控与配件有关的事件</h3><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">当配件接入或断开时，External Accessory框架都可以发送<dfn class="pediaLink"><span class="pediaLink" data-header="通告" data-contents="通告是发给一个或多个观察者对象的消息，目的是通知它们程序中发生的事件。" style="color: #3366cc; text-decoration: none; font-style: normal; border-bottom-width: 1px; border-bottom-style: dashed; border-bottom-color: #3366cc; white-space: nowrap; cursor: pointer; -webkit-transition-property: color, background-color, border-bottom, border-top-left-radius, border-top-right-radius, padding, margin; -webkit-transition-duration: 0.25s; "><a href="http://www.apple.com.cn/developer/iphone/library/documentation/General/Conceptual/DevPedia-CocoaCore/Notification.html#//apple_ref/doc/uid/TP40008195-CH35" target="_top" style="color: #3366cc; text-decoration: none; ">通告</a></span></dfn>。但是这些通告并不自动发送，如果您的应用程序感兴趣，必须调用EAAccessoryManager类的<a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EAAccessoryManager_class/Reference/Reference.html#//apple_ref/occ/instm/EAAccessoryManager/registerForLocalNotifications" target="_top" style="color: #3366cc; text-decoration: none; ">registerForLocalNotifications</a>方法来显式请求。当配件接入、认证、并准备好和应用程序进行交互时，框架可以发出一个<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EAAccessoryManager_class/Reference/Reference.html#//apple_ref/c/data/EAAccessoryDidConnectNotification" target="_top" style="color: #3366cc; text-decoration: none; ">EAAccessoryDidConnectNotification</a></code>通告；而当配件断开时，框架则可以发送一个<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EAAccessoryManager_class/Reference/Reference.html#//apple_ref/c/data/EAAccessoryDidDisconnectNotification" target="_top" style="color: #3366cc; text-decoration: none; ">EAAccessoryDidDisconnectNotification</a></code>通告。您可以通过缺省的<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/Cocoa/Reference/Foundation/Classes/NSNotificationCenter_Class/Reference/Reference.html#//apple_ref/occ/cl/NSNotificationCenter" target="_top" style="color: #3366cc; text-decoration: none; ">NSNotificationCenter</a></code>来注册接收这些通告。两种通告都包含受影响的配件的信息。</p><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">除了通过缺省的通告中心接收通告之外，当前正在和配件进行交互的应用程序可以为相应的<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; ">EAAccessory</code>对象分配一个<dfn class="pediaLink"><span class="pediaLink" data-header="委托" data-contents="委托是一种简单而强大的模式。在这种模式中，一个对象可以代表另一个对象进行动作或协调它的行为。" style="color: #3366cc; text-decoration: none; font-style: normal; border-bottom-width: 1px; border-bottom-style: dashed; border-bottom-color: #3366cc; white-space: nowrap; cursor: pointer; -webkit-transition-property: color, background-color, border-bottom, border-top-left-radius, border-top-right-radius, padding, margin; -webkit-transition-duration: 0.25s; "><a href="http://www.apple.com.cn/developer/iphone/library/documentation/General/Conceptual/DevPedia-CocoaCore/Delegation.html#//apple_ref/doc/uid/TP40008195-CH14" target="_top" style="color: #3366cc; text-decoration: none; ">委托</a></span></dfn>，使它在发生变化的时候得到通知。委托对象必须遵循<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EAAccessoryDelegate_protocol/Reference/Reference.html#//apple_ref/occ/intf/EAAccessoryDelegate" target="_top" style="color: #3366cc; text-decoration: none; ">EAAccessoryDelegate</a></code><dfn class="pediaLink"><span class="pediaLink" data-header="协议" data-contents="协议用于声明某种编程接口，任何类都可以选择实现这种接口。" style="color: #3366cc; text-decoration: none; font-style: normal; border-bottom-width: 1px; border-bottom-style: dashed; border-bottom-color: #3366cc; white-space: nowrap; cursor: pointer; -webkit-transition-property: color, background-color, border-bottom, border-top-left-radius, border-top-right-radius, padding, margin; -webkit-transition-duration: 0.25s; "><a href="http://www.apple.com.cn/developer/iphone/library/documentation/General/Conceptual/DevPedia-CocoaCore/Protocol.html#//apple_ref/doc/uid/TP40008195-CH45" target="_top" style="color: #3366cc; text-decoration: none; ">协议</a></span></dfn>，该协议目前包含名为<code style="font-size: 12px; font-family: Courier, Consolas, monospace; color: #666666; "><a href="http://developer.apple.com/iphone/library/documentation/ExternalAccessory/Reference/EAAccessoryDelegate_protocol/Reference/Reference.html#//apple_ref/occ/intfm/EAAccessoryDelegate/accessoryDidDisconnect:" target="_top" style="color: #3366cc; text-decoration: none; ">accessoryDidDisconnect:</a></code>的可选方法，您可以通过这个方法来接收配件断开通告，而不需要事先配置通告观察者。</p><p style="margin-top: 0px; margin-bottom: 0.833em; font: normal normal normal 100%/normal 'Lucida Grande', Geneva, Helvetica, Arial, sans-serif; ">有关如何注册接收通告的更多信息，请参见<em><a href="http://developer.apple.com/iphone/library/documentation/Cocoa/Conceptual/Notifications/index.html#//apple_ref/doc/uid/10000043i" target="_top" style="color: #3366cc; text-decoration: none; ">Cocoa通告编程主题</a></em>。</p></span><font class="Apple-style-span" face="Verdana" size="2"><div><div><span style="line-height: normal;"><br /><br /></span></div></div></font><img src ="http://www.cppblog.com/Khan/aggbug/157871.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2011-10-09 14:47 <a href="http://www.cppblog.com/Khan/archive/2011/10/09/157871.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>移动智能网</title><link>http://www.cppblog.com/Khan/archive/2010/10/26/131312.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Tue, 26 Oct 2010 03:18:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2010/10/26/131312.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/131312.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2010/10/26/131312.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/131312.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/131312.html</trackback:ping><description><![CDATA[. 智能网<br>PSTN Public Switched Telephone Network 公共交换电话网络<br>PLMN Public Land Mobile Network 公共陆地移动网络<br>IN&nbsp;&nbsp; Intelligent Network 智能网<br>INCM Intelligent Netwrok Conceptual Model 智能网概念模型<br><br>SCE&nbsp; Service Creation Environment 业务创建环境<br>SMP&nbsp; Service Management Point 业务管理点<br>SCP&nbsp; Service Control Point 业务控制点<br>SSP&nbsp; Service Switching Point 业务交换点<br>IP&nbsp;&nbsp; Intelligent Peripheral 智能外设<br>SMAP Service Management Access Point 业务管理接入点<br>SS7&nbsp; Signaling System #7 7号信令系统<br><br>&nbsp;&nbsp;&nbsp; 一项新业务由SCE生成,经过验证后由SMP提交给SCP. 业务在SCP内执行,业务的一次执行由SCP与SSP共同协作完成. IP提供智能网业务所需的专用资源.在业务执行的过程中,SCP<br><br>控制IP向用户播放录音通知和收集拨号数据等.<br>&nbsp;&nbsp;&nbsp; 此外,智能网体系结构中还包含SMAP,向用户提供接入到SMP以及对智能网业务及节点进行管理的接口.<br>&nbsp;&nbsp;&nbsp; IN结构网中,SCP与SSP,IP通过SS7互联,完成业务的呼叫控制;SCP与SMP经公用数据网(如X.25)连接,完成业务系统的管理 网络管理以及接入管理的控制.<br><br><br><br><br>. 蜂窝移动通信系统的组成<br>BTS&nbsp;&nbsp; Base Transeiver Station 基站收发信台<br>BSC&nbsp;&nbsp; Base Sation Controller 基站控制器<br>MSC&nbsp;&nbsp; Mobile Switching Center 移动业务交换中心<br>VLR&nbsp;&nbsp; Visitor Location Register 访问位置寄存器<br>HLR&nbsp;&nbsp; Home Location Register 归属位置寄存器<br>OMC&nbsp;&nbsp; Operation and Maintenance Center 操作维护中心<br>AC&nbsp;&nbsp;&nbsp; Authentication Center 鉴权中心<br>MS&nbsp;&nbsp;&nbsp; Mobile Station 移动台<br><br>GSM&nbsp;&nbsp; Global System for Mobile Communication 全球移动通信系统<br>SIM&nbsp;&nbsp; Subscriber Identifier Module 客户识别模块<br><br>CAMEL Customized Application for Mobile Network Enhanced Logic 移动网络增强定制应用逻辑<br><br>&nbsp;&nbsp;&nbsp; 我国的移动智能网建设是基于CAMEL2阶段标准的.<br><br>CAMEL2支持的业务及特征<br>CAMEL2阶段可提供如下类型的业务:<br>. 虚拟专用网 VPN (Virtual Private Netwrok)<br>. 先进的选路业务<br>. 屏蔽业务(入呼叫 出呼叫)<br>. 预付费业务(Prepaid Service)<br>. 使用限制(Usage Limitation)<br>. 基于位置的业务LBS(Location Based Service)<br><br>CAMEL2阶段需要支持如下特征:<br>. 移动发起和前转的呼叫<br>. 移动终止的呼叫<br>. 随时的查询(运营者可选)<br>. 消除录音的通知<br>. 录音通知和带内信息交互<br>. 计费信息<br>. 补充业务调用通知<br><br>CAMEL业务不属于GSM紧急呼叫业务, 因此用户紧急呼叫时不会触发CAMEL业务<br><br><br><br><br>. GSM移动智能网<br>CAP&nbsp;&nbsp;&nbsp; CAMEL Application Part CAMEL应用部分<br>MAP&nbsp;&nbsp;&nbsp; Mobile Application Part 移动应用部分<br>ETSI&nbsp;&nbsp; European Telecommunications Sdandards Institute 欧洲电信标准协会<br>3GPP&nbsp;&nbsp; ETSI 3rd Generation Partnership Project 第三代合作伙伴计划<br>DP&nbsp;&nbsp;&nbsp;&nbsp; Detection Point 检测点<br>CSI&nbsp;&nbsp;&nbsp; CAMEL Subscriber Information CAMEL客户化签约数据<br>BCSM&nbsp;&nbsp; Basic Call State Model 基本呼叫状态模型<br>gsmCCF GSM Call Control Function GSM呼叫控制功能<br>gsmSCF GSM Service Control Function GSM业务控制功能<br>gsmSSF GSM Service Switching Function GSM业务交换功能<br>gsmSRF GSM Specialized Resource Function GSM专用资源功能<br>USSD&nbsp;&nbsp; Unstructured Supplementary Service Data 非结构化补充数据业务<br><br>CAMEL标准的组成<br>1. 业务描述 CAMEL2阶段 在ETSI所有规范中编号为ETSI TS 101 285, 在GSM系统中编号为GSM 02.78. CAMEL3阶段ETSI相应的协议编号为ETSI TS 122 078, 在移动系统中的编号为<br><br>3G TS 22.078<br>2. 第二步描述 对支持CAMEL业务实现的机制进行详细描述. 在CAMEL1,CAMEL2阶段, 这部分标准在ETSI中的编号为ETSI TS 101 441, 在GSM系统中的编号为GSM 03.78. 到CAMEL3阶<br><br>段相应的协议编号变为ETSI TS 123 078,在移动系统中的编号为3G TS 23.078<br>3. CAMEL应用协议CAP的定义 在CAMEL1 CAMEL2阶段, 这部分标准在ETSI中的编号为ETSI TS 101 046, 在GSM系统中的编号为GSM 09.78. 到CAMEL3阶段相应的协议编号变为ETSI TS <br><br>129 078, 在移动系统中的编号为3G TS 29.078<br><br><br>CAMEL标准的内容<br>. CAMEL体系结构&nbsp; 包括CAMEL系统在分布功能平面的体系结构, 功能实体以及CAMEL标准化接口<br>. CAMEL监测点&nbsp; 包括CAMEL标准定义的检测点及处理规则<br>. CAMEL客户化签约数据的描述&nbsp; CSI是CAMEL标准中的关键概念,包括始发呼叫CSI和终止呼叫CSI等等. <br>. CAMEL基本呼叫状态模型 包括发端BCSM以及终端BCSM<br>. CAMEL处理过程介绍<br>. CAMEL信息流定义<br>. 与移动交换系统补充业务的交互原则<br><br><br>CAMEL标准的演进<br>.CAMEL1<br>&nbsp;CAMEL1标准与1997年推出. <br>&nbsp;&nbsp;&nbsp; 与GSM原有系统相比,增加了gsmSCF,gsmSSF功能实体. <br>&nbsp;&nbsp;&nbsp; 确定如下接口:gsmSCF与gsmSSF之间的CAP接口, gsmSCF与HLR之间, HLR与VLR之间, HLR与GMSC之间的MAP接口<br>&nbsp;&nbsp;&nbsp; 定义了7条CAP操作<br>.CAMEL2<br>&nbsp;CAMEL2标准与1998年推出, 并于1999年冻结. 与CAMEL1相比<br>&nbsp;&nbsp;&nbsp; 增加了gsmSRF功能实体<br>&nbsp;&nbsp;&nbsp; 增加了如下接口: gsmSCF与gsmSRF之间的CAP接口, gsmSCF与MSC之间的MAP接口<br>&nbsp;&nbsp;&nbsp; 定义了22条CAP操作<br>&nbsp;&nbsp;&nbsp; 增加了gsmSCF与HLR之间的USSD接口<br>.CAMEL3 <br>&nbsp;&nbsp;&nbsp; CAMEL3标准尚未定义<br><br><br><br><br>.CAMEL签约信息的基本概念<br>O-CSI&nbsp;&nbsp; Originating CAMEL Subscriber Information 发端CAMEL签约信息<br>T-CSI&nbsp;&nbsp; Terminating CAMEL Subscriber Information 终端CAMEL签约信息<br>SS-CSI&nbsp; Supplementary Service Notification CAMEL Subscriber&nbsp; Information 补充业务通知CAMEL签约信息<br>TIF-CSI Translation Information Flag CAMEL Subscriber Information 翻译信息标记CAMEL签约信息<br>U-CSI&nbsp;&nbsp; USSD CAMEL Subscriber Information USSD CAMEL签约信息<br>UG-CSI&nbsp; USSD General CAMEL Subscriber Information USSD通用CAMEL签约信息 如果一个用户既有U-CSI,又有UG-CSI,则U-CSI有着更高的优先级<br><br>&nbsp; HLR <br>&nbsp;&nbsp;&nbsp; HLR通常是一个数据库, 其中存放着全部归属用户的信息,如用户的有关号码(IMSI和MS ISDN)及用户类别. HLR还存储着每个归属用户有关的动态数据信息, 如用户现在所在的<br><br>MSC/VLR地址(即位置信息)和分配给用户的补充业务.<br>&nbsp;&nbsp;&nbsp; HLR还和gsmSCF有一个接口, 以便随时提供询问信息,不过这是营运者可以选择的.<br>&nbsp;&nbsp;&nbsp; 当支持此功能时,gsmSCF向HLR请求用户的状态和位置信息,HLR向VLR询问相应的信息后回发给gsmSCF.<br><br>&nbsp; VLR和MSC&nbsp;&nbsp; &nbsp;<br>&nbsp;&nbsp;&nbsp; VLR为拜访位置寄存器, MSC为移动交换中心,因为二者之间的信息流量特别大,因此二者通常在一个物理实体中. MSC/VLR主要功能是完成呼叫交换,并控制移动台的位置更新和<br><br>越区切换过程. 其中,MSC主要负责呼叫的建立(包括鉴权程序) 呼叫控制和计费等功能; 而VLR则主要负责存储和更新用户数据, 这些移动用户是那些漫游到该VLR所辖区中的移动用<br><br>户. <br>&nbsp;&nbsp;&nbsp; 为了支持CAMEL业务, VLR需要能存储CAMEL的用户信息, 当用户漫游到某个VLR区域时, 此VLR将O-CSI和SS-CSI作为部分用户数据存储在数据库中, 当处理需要CAMEL支持的业务<br><br>时, MSC从VLR接收到O-CSI信息, 并向gsmSSF请求指示. 在处理过程中,MSC件事请求的呼叫并通知gsmSSF其状态. 当处理调用任意的补充业务时, MSC从VLR接收SS-CSI,并指出应向<br><br>gsmSCF发送补充业务调用.<br><br>&nbsp; GMSC<br>&nbsp;&nbsp;&nbsp; GMSC为关口移动交换中心. 为了找到漫游中的移动用户, 通常需要向HLR查询该移动用户的所有信息. 因此必须在移动通信网的入口处(即与固定网相连点)使用一个GMSC来提供<br><br>所有入网呼叫的查询和转接能力. 因此, GMSC应具有从HLR中查询该移动用户当前位置信息的功能, 并能根据该信息重选呼叫该移动用户的路由以转接该呼叫.<br>&nbsp;&nbsp;&nbsp; 为了支持CAMEL业务, 当处理需要CAMEL支持的业务时,GMSC从HLR接收到O/T-CSI信息, 并向gsmSSF请求指示. 在处理过程中, GMSC监视请求的呼叫状态并通知gsmSSF其状态. <br><br>.CAMEL网络结构中的新增智能网实体<br>&nbsp;&nbsp;&nbsp; 新增的智能网实体有gsmSSF和gsmSCF.<br>&nbsp;&nbsp;&nbsp; gsmSSF为gsm业务交换功能, gsmSCF为gsm业务控制功能, 他们各自的功能同智能网中的SSF与SCF功能基本相同.<br><br>&nbsp; gsmSSF<br>&nbsp;&nbsp;&nbsp; gsmSSF作为MSC/VLR与gsmSCF之间的接口, 负责将MSC报告的呼叫状态信息进行转化, 然后发给gsmSCF或者接受gsmSCF指示, 进行格式转化, 再发给MSC.<br><br>&nbsp; gsmSCF<br>&nbsp;&nbsp;&nbsp; gsmSCF是实现业务核心, 是一个动态的数据库和事物处理单元, 负责执行CAMEL业务逻辑, 以实现执行特定的业务 控制呼叫的接续和计费等, 他是移动智能网的中心.<br><br><br>.CAMEL网络结构中的协议及功能实体的分布<br>&nbsp;&nbsp;&nbsp; 所用到的协议有CAP和MAP, CAP的全称为CAMEL应用部分(CAMEL Application part), 应用在两个智能网实体(此处为gsmSSF与gsmSCF)之间; MAP全称为移动应用部分(Mobile <br><br>Application Part), 应用在GSM实体之间或GSM实体与智能网实体之间(此处为HLR与gsmSSF, HLR与VLR, HLR与GMSC之间).<br>&nbsp;&nbsp;&nbsp; HLR与gsmSCF组成归属网络, 代表了用户的归属性质. GMSC与gsmSSF组成询问网络, 主要针对移动用户作为被叫的呼叫而言. MSC/VLR/gsmSSF组成拜访网络, 主要针对移动用户<br><br>作为主叫而言.<br>&nbsp;&nbsp;&nbsp; CAMEL1的最大缺陷在于没有SRF功能, 因此采用CAMEL1实现一些智能业务时系统与用户之间几乎没有语音交互. 为了增加用户交互的友好性, 不得不增加专门的交互语音资源<br><br>(IVR:Interaction Voice Resource)设备. 另外CAMEL1没有很好的解决GSM补充业务与CAMEL业务之间存在的交互问题. 而CAMEL2中增加MSC与gsmSCF之间的接口为解决这个问题提供<br>了基础.<br><br><br>.CAMEL2网络结构<br>&nbsp;&nbsp;&nbsp; CAMEL2的功能结构与CAMEL1基本相似, 只是在CAMEL的功能结构基础上又增加了一些实体和实体之间的接口, 另外协议功能也有所增强.<br><br>&nbsp; 新增gsm特殊资源功能gsmSRF<br>&nbsp;&nbsp;&nbsp; 同CAMEL1的功能结构相比, CAMEL2中增加一个功能实体gsmSRF, 他是一个智能网的功能实体, 同SRF的功能基本相同, 主要用于提供各种特定的资源, 例如提示语音资源和二次<br><br>收号器, 他与MSC, gsmSCF有接口.<br><br>&nbsp; 新增接口<br>&nbsp;&nbsp;&nbsp; 除gsmSRF与其他功能实体的接口外, 与CAMEL1相比, 在CAMEL2中还增加了MSC与gsmSCF之间的接口, 用于MSC想gsmSCF通知所调用的补充业务.<br><br><br><br>.CAMEL协议<br>&nbsp; CAP协议<br>&nbsp;&nbsp;&nbsp; CAP主要用在gsmSSF和gsmSCF, gsmSCF和gsmSRF之间, CAP是基于智能网的INAP协议, 主要是基于CS1的INAP协议, CS1一共有29条INAP操作, CAMEL仅仅用了其中的几条, 操作的<br><br>名称相同, 但是其中的参数有所不同. 在CAMEL1中, 没有gsmSRF功能实体, 仅仅有功能实体gsmSSF和gsmSCF, 所用的CAP协议仅仅有7条操作, CAMEL2中增加了gsmSRF功能实体, CAP<br><br>的信息流也增加为22条. <br>&nbsp;&nbsp;&nbsp; CAMEL1的7条操作为: ActiveTest, Connect, Continue, EventReportBCSM, InitalDP, ReleaseCall, RequestReportBCSMEvent.<br>&nbsp;&nbsp;&nbsp; CAMEL2中新增的15条操作为: ApplyCharging, ApplyChargingReport, ConnectToResource, CallInformationReport, CallInformationRequest, <br><br>FurnishChargingInformation, SendChargingInformation, PlayAnnouncement, PromptAndCollectUserInforamtion, Cancel, SpecialisedResourceReport, RestTimer, <br><br>DisconnectForwardConnection, AssistRequest, EstablishTemporaryConnection.<br>&nbsp; <br>&nbsp; MAP协议<br>&nbsp;&nbsp;&nbsp; 当前普通的GSM网络所用的MAP协议为MAP Phase2协议, 为了实现移动网与智能网的互联, 提供CAMEL业务, 就需要对现有的MAP协议进行升级, 升级为MAP Phase2+协议. MAP <br><br>Phase2+协议是为了实现CAMEL业务而对原有的MAP Phase2协议做了一些修改, 增加了HLR与gsmSCF, gsmSCF与MSC之间的接口程序, 并在原有的程序中增加了涉及到CAMEL签约信息的<br><br>参数等内容.<br>&nbsp;&nbsp;&nbsp; gsmSCF与HLR之间的信息流主要是gsmSCF在任意时间向HLR询问用户信息的请求以及HLR对此请求的响应. 响应者可以选择HLR接受gsmSCF的请求或拒绝请求. <br><br><br><br><br><br><br><br><br><br><br><br>&nbsp;<br>  <img src ="http://www.cppblog.com/Khan/aggbug/131312.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2010-10-26 11:18 <a href="http://www.cppblog.com/Khan/archive/2010/10/26/131312.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Tcp/IP数据包分析</title><link>http://www.cppblog.com/Khan/archive/2010/01/21/106122.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 21 Jan 2010 04:38:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2010/01/21/106122.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/106122.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2010/01/21/106122.html#Feedback</comments><slash:comments>4</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/106122.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/106122.html</trackback:ping><description><![CDATA[<span style="font-family: courier new;">10:08:51.006836 IP 58.16.246.110.25479 &gt; 58.16.246.220.5016: P 33025:33041(16) ack 33228 win 5840</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 0x0000:&nbsp; 4500 0038 d14f 4000 4006 0805 3a10 f66e&nbsp; E..8.O@.@...:..n</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 0x0010:&nbsp; 3a10 f6dc 6387 1398 2e78 1088 5a1a ac28&nbsp; :...c....x..Z..(</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 0x0020:&nbsp; 5018 16d0 6196 0000 0000 000c 8000 0015&nbsp; P...a...........</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 0x0030:&nbsp; 0000 0000 a716 f4f8&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ........<br><br style="font-family: courier new;"><span style="font-family: courier new;">IP Header</span><br style="font-family: courier new;"><span style="font-family: courier new;">45</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp; 4&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //协议版本 ipv4&nbsp;&nbsp;&nbsp; 4bit</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp; 5&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //IHL位 20字节, 表示IP Header长度 以32bit为除数计算出的IP头部长度&nbsp;&nbsp; 本区域值 = IP头部长度 / 32 最长的IP包头长度可以为480bit</span><br style="font-family: courier new;"><span style="font-family: courier new;">00&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; // 服务类型 Type of Service</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp; &nbsp; Precedence和TOS。定义IP协议包的处理方法，它包含如下子字段</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 过程字段(优先权)：3位，设置了数据包的重要性，取值越大数据越重要，取值范围为：0(正常)~ 7（网络控制) </span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 延迟(时延)字段：1位，取值：0(正常)、1(期特低的延迟) </span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 流量(吞吐量)字段：1位，取值：0(正常)、1(期特高的流量) </span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 可靠性字段：1位，取值：0(正常)、1(期特高的可靠性) </span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 成本(开销)字段：1位，取值：0(正常)、1(期特最小成本) </span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 未使用(保留位)：1位,恒设为0</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; TOS目前不太使用。而Precedence则用于QOS应用。(TOS字段的详细描述RFC 1340 1349)</span><br style="font-family: courier new;"><span style="font-family: courier new;">00 38&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //IP数据报文总长</span><br style="font-family: courier new;"><span style="font-family: courier new;" lang="ZH-CN">d1 4f&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //标识符(Identifier):长度16比特。该字段和Flags和Fragment Offest字段联合使用，对大的上层数据包进行分段(fragment)操作。如果数据包原始长度超过MTU,那么将他分段为更小的数据包.然后路由器在每片数据包的标志字段打上相同的标记,以便接收设备可以识别出属于一个数据包的分段.分段的数据包不会在数据链路的另外一端重新组合,直到最终目的地才会重组.</span><br style="font-family: courier new;"><span style="font-family: courier new;" lang="ZH-CN">40 00&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //标记(Flags)：长度3比特&nbsp; 分段序号(Fragment Offset)：长度13比特</span><br style="font-family: courier new;"><span style="font-family: courier new;">40&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //TTL</span><br style="font-family: courier new;"><span style="font-family: courier new;" lang="ZH-CN">06&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //协议(Protocol)：长度8比特。标识了上层所使用的协议。TCP=06 UDP=17 ICMP=01 其他请查看cat /etc/protocols</span><br style="font-family: courier new;"><span style="font-family: courier new;" lang="ZH-CN">08 05&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //头部校验(Header Checksum)：长度16位，由于IP包头是变长的，所以提供一个头部校验来保证IP包头中信息的正确性。</span><br style="font-family: courier new;"><span style="font-family: courier new;">3a 10 f6 6e&nbsp;3a 10 f6 dc </span><br style="font-family: courier new;"><br style="font-family: courier new;"><span style="font-family: courier new;">tcp Header</span><br style="font-family: courier new;"><span style="font-family: courier new;">6387&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //src port&nbsp; 本地端口25479</span><br style="font-family: courier new;"><span style="font-family: courier new;">1398&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //dest port 目标端口5016</span><br style="font-family: courier new;"><span style="font-family: courier new;">2e78 1088&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //Sequence Number 顺序号</span><br style="font-family: courier new;"><span style="font-family: courier new;">5a1a ac28&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //ack num 确认号</span><br style="font-family: courier new;"><span style="font-family: courier new;">5018&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //tcp头长度 20字节&nbsp;&nbsp; 5018&nbsp; 2进制01010000 00011000</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp;&nbsp;&nbsp; 5 0101&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //表示tcp长度 20字节</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp; &nbsp; 0000 00&nbsp;&nbsp;&nbsp;&nbsp; //保留 无意义</span><br style="font-family: courier new;"><span style="font-family: courier new;">&nbsp; &nbsp; 011000&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; //6bit 标志位</span><br style="font-family: courier new;">
<p style="font-family: courier new;">&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; URG: (Urgent Pointer field significant)紧急指针。用到的时候值为1，用来处理避免TCP数据流中断<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ACK: (Acknowledgment fieldsignificant)置1时表示确认号(AcknowledgmentNumber)为合法，为0的时候表示数据段不包含确认信息，确认号被忽略。　<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; PSH: (Push Function)，PUSH标志的数据，置1时请求的数据段在接收方得到后就可直接送到应用程序，而不必等到缓冲区满时才传送。　<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; RST: (Reset the connection)用于复位因某种原因引起出现的错误连接，也用来拒绝非法数据和请求。如果接收到RST位时候，通常发生了某些错误。　<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; SYN: (Synchronize sequence numbers)用来建立连接，在连接请求中，SYN=1，ACK=0，连接响应时，SYN=1，ACK=1。即，SYN和ACK来区分 Connection Request和Connection Accepted。　<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; FIN: (No more data from sender)用来释放连接，表明发送方已经没有数据发送了。　</p>
<span style="font-family: courier new;">
16d0 6196 0000 </span><br style="font-family: courier new;"><br style="font-family: courier new;"><span style="font-family: courier new;">data</span><br style="font-family: courier new;"><span style="font-family: courier new;">0000 000c 8000 0015 0000 0000 a716 f4f8&nbsp;&nbsp; //承载的数据体<br><br><br></span>  <img src ="http://www.cppblog.com/Khan/aggbug/106122.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2010-01-21 12:38 <a href="http://www.cppblog.com/Khan/archive/2010/01/21/106122.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>图形学基础(一)</title><link>http://www.cppblog.com/Khan/archive/2009/07/14/90067.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Tue, 14 Jul 2009 10:05:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2009/07/14/90067.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/90067.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2009/07/14/90067.html#Feedback</comments><slash:comments>3</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/90067.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/90067.html</trackback:ping><description><![CDATA[直线的笛卡尔斜率截距方程为<br>y=m*x+b<br>m直线的斜率<br>b是y轴的截距<br><br>给定线段的两个端点(x1,y1) 和(x2,y2 )可以计算斜率m和截距b<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; y2-y1<br>m = ----------<br>&nbsp;&nbsp;&nbsp; &nbsp; &nbsp;&nbsp; x2-x1<br><br>b = y1-m*x1<br><br><br>　　斜率，亦称&#8220;角系数&#8221;，表示一条直线相对于横坐标轴的倾斜程度。一条直线与某平面直角坐标系横坐标轴正半轴方向的夹角的正切值即该直线相对于该坐标系的斜率。<br>
如果直线与x轴互相垂直，直角的正切直无穷大，故此直线，不存在斜率。<br>
对于一次函数y=kx+b，k即该函数图像的斜率。<br>
对于任意函数上任意一点，其斜率等于其切线与x轴正方向的夹角，即tan&#945;. <br>
斜率计算：ax+by+c=0中，k=-a/b.<br><br>
<pre>X轴上截距：与X轴交点横坐标。<br>Y轴上截距：与Y轴交点纵坐标。<br>截距是实数，不是&#8220;距离&#8221;，可正可负。<br>截距之和即：X轴上截距与Y轴上截距之和。</pre>
<br><br><br><br> <img src ="http://www.cppblog.com/Khan/aggbug/90067.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2009-07-14 18:05 <a href="http://www.cppblog.com/Khan/archive/2009/07/14/90067.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>NO.7 信令系统基本功能结构</title><link>http://www.cppblog.com/Khan/archive/2009/07/01/88998.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Wed, 01 Jul 2009 08:16:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2009/07/01/88998.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/88998.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2009/07/01/88998.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/88998.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/88998.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: No.7  SS7&nbsp;&nbsp;<a href='http://www.cppblog.com/Khan/archive/2009/07/01/88998.html'>阅读全文</a><img src ="http://www.cppblog.com/Khan/aggbug/88998.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2009-07-01 16:16 <a href="http://www.cppblog.com/Khan/archive/2009/07/01/88998.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>7bit_default_table pud格式7bit编码对应表</title><link>http://www.cppblog.com/Khan/archive/2009/05/08/82240.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Fri, 08 May 2009 07:45:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2009/05/08/82240.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/82240.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2009/05/08/82240.html#Feedback</comments><slash:comments>3</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/82240.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/82240.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp;&nbsp; 摘要: &nbsp;&nbsp; &nbsp;GSM 3.38中定义的pdu格式编码, 其中7bit的部分不光要处理常见的ascii编码, 还要处理一些欧洲字符, 这些字符不在常规的127个ascii字符中, 所以需要如下映射表做一个映射, 另有部分字符与在ascii中的位置不一致, 所以千万要注意. 网上不少山寨代码都忽略协议. 想当然的实现了所谓的pdu编码格式. 忧郁中.    &nbsp;...&nbsp;&nbsp;<a href='http://www.cppblog.com/Khan/archive/2009/05/08/82240.html'>阅读全文</a><img src ="http://www.cppblog.com/Khan/aggbug/82240.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2009-05-08 15:45 <a href="http://www.cppblog.com/Khan/archive/2009/05/08/82240.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>ubuntu 下安装wine</title><link>http://www.cppblog.com/Khan/archive/2008/05/23/50909.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Fri, 23 May 2008 15:18:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2008/05/23/50909.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/50909.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2008/05/23/50909.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/50909.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/50909.html</trackback:ping><description><![CDATA[编译源码的方式就不写了， 无非就是解决依赖关系， down一堆的包， 然后make<br>简单粗暴的来......<br><br>1.安装<br>sudo apt-get install <span class="hilite1">wine<br><br>2.初始化<br>winecfg&nbsp; //不要用root模式, 也就是不要用sudo<br><br>如果出现以下警告或者错误:<br></span><span class="postbody">preloader: Warning: failed to reserve range 00000000-60000000
<br>
err:dosmem:setup_dos_mem Cannot use first megabyte for DOS address space, please report
</span><br><br>解决方法: 其实我不清楚为什么要这么做....唉.....<br><span class="postbody">sudo sysctl -w vm.mmap_min_addr=0
<br>
<br>
然后打开sysctl.conf
<br>
sudo gedit /etc/sysctl.conf
<br>
<br>
#vm.mmap_min_addr = 65536&nbsp;
//注释掉这行<br>
vm.mmap_min_addr = 0&nbsp;
//改为这行</span><br><span class="hilite1"><br><br></span>
<p>3、设置中文问题</p>
<p>&nbsp;&nbsp; 先把字体simsun.ttc（在你的windows的<span class="hilite2">安装</span>目录里的font文件夹里找，找不到可以从网上下到） 复制到 /home/你的用户名/.<span class="hilite1">wine</span>/drive_c/windows/fonts 文件夹中，<span style="color: #ff0000; font-size: small;">要显示隐藏文件夹按Ctrl+H</span>
</p>
<br>
<p>&nbsp; 修改注册表，在命令行输入 gedit&nbsp; ~/.<span class="hilite1">wine</span>/system.reg</p>
<p>&nbsp; 找到&#8220;[System\\CurrentControlSet\\Hardware
Profiles\\Current\\Software\\Fonts]&#8221;，将其中的&#8220;&#8220;LogPixels&#8221;=dword:00000060&#8221;改成
&#8220;&#8220;LogPixels&#8221;=dword:00000070&#8220;。<br>
<br>
再找到&#8221;[Software\\Microsoft\\Windows NT\\CurrentVersion\\FontSubstitutes] xxxx&#8220;项，将其中的&#8221;MS Shell Dlg&#8220;相关的两项修改成如下内容（即更换字体为宋体）：<br>
<br>
&#8220;MS Shell Dlg&#8221;=&#8221;SimSun&#8221;<br>
&#8220;MS Shell Dlg 2&#8243;=&#8221;SimSun&#8221;<br>
<br>
然后：gedit ~/.<span class="hilite1">wine</span>/drive_c/windows/win.ini</p>
<p>在其中加上（如果没有），有的话修改成如下</p>
<p> [Desktop]<br>
menufontsize=13<br>
messagefontsize=13<br>
statusfontsize=13<br>
IconTitleSize=13</p>
<p>现在中文显示应该正常了</p>
<br><span class="hilite1"><br></span><img src ="http://www.cppblog.com/Khan/aggbug/50909.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2008-05-23 23:18 <a href="http://www.cppblog.com/Khan/archive/2008/05/23/50909.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>通过两个点的经纬度计算距离</title><link>http://www.cppblog.com/Khan/archive/2008/02/28/43390.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 28 Feb 2008 07:18:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2008/02/28/43390.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/43390.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2008/02/28/43390.html#Feedback</comments><slash:comments>11</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/43390.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/43390.html</trackback:ping><description><![CDATA[最近开始做一个类似gis的东西. 需要求一些经纬度相关的值..<br><br>看了<a href="http://panyee.cnblogs.com/archive/2006/07/04/442771.html" target="_blank">通过两个点的经纬度计算距离</a>这篇，据说是Google里扒来的算法，于是决定验证一下。<br>通过计算发现非常正确。<br>用30,120和31,121两个坐标点进行验证，同Mapinfo中计算的结果非常的相近。<br>后来又把坐标系直接当成直角坐标系来计算，发现误差很大。<br>于是仍然用直角坐标系方法来计算，给纬度加上了个0.86的参数，这样计算下来和结果相近。<br><br><br><br><br>c#代码<br>private const double EARTH_RADIUS = 6378.137; //地球半径<br>private static double rad(double d)<br>{<br>&nbsp;&nbsp;&nbsp;return d * Math.PI / 180.0;<br>}
<p>public static double GetDistance(double lat1, double lng1, double lat2, double lng2)<br>{<br>&nbsp;&nbsp;&nbsp;double radLat1 = rad(lat1);<br>&nbsp;&nbsp;&nbsp;double radLat2 = rad(lat2);<br>&nbsp;&nbsp;&nbsp;double a = radLat1 - radLat2;<br>&nbsp;&nbsp;&nbsp;double b = rad(lng1) - rad(lng2);<br>&nbsp;&nbsp;&nbsp;double s = 2 * Math.Asin(Math.Sqrt(Math.Pow(Math.Sin(a/2),2) + <br>&nbsp;&nbsp;&nbsp;&nbsp;Math.Cos(radLat1)*Math.Cos(radLat2)*Math.Pow(Math.Sin(b/2),2)));<br>&nbsp;&nbsp;&nbsp;s = s * EARTH_RADIUS;<br>&nbsp;&nbsp;&nbsp;s = Math.Round(s * 10000) / 10000;<br>&nbsp;&nbsp;&nbsp;return s;<br>}</p>
<br>
<p>vb代码</p>
<img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Const&nbsp;EARTH_RADIUS&nbsp;=&nbsp;6378.137<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Const&nbsp;Pi&nbsp;=&nbsp;3.1415926535898<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top"><br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Function&nbsp;rad(ByVal&nbsp;d&nbsp;As&nbsp;Double)&nbsp;As&nbsp;Double<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">rad&nbsp;=&nbsp;d&nbsp;*&nbsp;Pi&nbsp;/&nbsp;180<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">End&nbsp;Function<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top"><br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Function&nbsp;GetDistance(lat1&nbsp;As&nbsp;Double,&nbsp;lng1&nbsp;As&nbsp;Double,&nbsp;lat2&nbsp;As&nbsp;Double,&nbsp;lng2&nbsp;As&nbsp;Double)&nbsp;As&nbsp;Double<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Dim&nbsp;radlat1&nbsp;As&nbsp;Double,&nbsp;radlat2&nbsp;As&nbsp;Double<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Dim&nbsp;a&nbsp;As&nbsp;Double,&nbsp;b&nbsp;As&nbsp;Double,&nbsp;s&nbsp;As&nbsp;Double,&nbsp;Temp&nbsp;As&nbsp;Double<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">radlat1&nbsp;=&nbsp;rad(lat1)<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">radlat2&nbsp;=&nbsp;rad(lat2)<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">a&nbsp;=&nbsp;radlat1&nbsp;-&nbsp;radlat2<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">b&nbsp;=&nbsp;rad(lng1)&nbsp;-&nbsp;rad(lng2)<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Temp&nbsp;=&nbsp;Sqr(Sin(a&nbsp;/&nbsp;2)&nbsp;^&nbsp;2&nbsp;+&nbsp;Cos(radlat1)&nbsp;*&nbsp;Cos(radlat2)&nbsp;*&nbsp;Sin(b&nbsp;/&nbsp;2)&nbsp;^&nbsp;2)<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">s&nbsp;=&nbsp;2&nbsp;*&nbsp;Atn(Temp&nbsp;/&nbsp;Sqr(-Temp&nbsp;*&nbsp;Temp&nbsp;+&nbsp;1))&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;'没有反正弦函数，网上找了个<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">s&nbsp;=&nbsp;s&nbsp;*&nbsp;EARTH_RADIUS<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">GetDistance&nbsp;=&nbsp;s<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">End&nbsp;Function<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top"><br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Private&nbsp;Sub&nbsp;Command1_Click()<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Text5.Text&nbsp;=&nbsp;Str(GetDistance(Val(Text1.Text),&nbsp;Val(Text2.Text),&nbsp;Val(Text3.Text),&nbsp;Val(Text4.Text)))<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">End&nbsp;Sub<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top"><br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Private&nbsp;Sub&nbsp;Command2_Click()<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Text5.Text&nbsp;=&nbsp;Str((Sqr((Val(Text3.Text)&nbsp;-&nbsp;Val(Text1.Text))&nbsp;^&nbsp;2&nbsp;+&nbsp;(Val(Text4.Text)&nbsp;-&nbsp;Val(Text2.Text))&nbsp;^&nbsp;2))&nbsp;*&nbsp;111.3199338)<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">End&nbsp;Sub<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top"><br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Private&nbsp;Sub&nbsp;Command3_Click()<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">Text5.Text&nbsp;=&nbsp;Str((Sqr((Val(Text3.Text)&nbsp;*&nbsp;0.86&nbsp;-&nbsp;Val(Text1.Text)&nbsp;*&nbsp;0.86)&nbsp;^&nbsp;2&nbsp;+&nbsp;(Val(Text4.Text)&nbsp;-&nbsp;Val(Text2.Text))&nbsp;^&nbsp;2))&nbsp;*&nbsp;111.3199338)<br><img src="http://tangf.cnblogs.com/Images/OutliningIndicators/None.gif" align="top">End&nbsp;Sub
<p><br></p>
<p><br></p>
同纬度计算比较简单<br>
<p>A（60，30），B（60，90）两点之间，此段代码和我用余弦定理算出来的结果很一致。
<br>余弦定理的步骤是：1、算A、B弦长：地球半径R*cos（经度差60）=R/2；
<br>2、算角AOB,O为地球圆心，利用余弦定理，
<br>cosAOB=(2R*R-(R/2)^2) /2*R*R=7/8;
<br>3、弧AB的长为：R*arc cos(7/8);求毕 <br></p>
<br>
<p><br></p>
<p>原理:<br></p>
<p>
地球赤道上环绕地球一周走一圈共40075.04公里,而@一圈分成360&#176;,而每1&#176;(度)有60,每一度一秒在赤道上的长度计算如下：
<br>
<br>　　40075.04km/360&#176;=111.31955km
<br>
<br>　　111.31955km/60=1.8553258km=1855.3m
<br>
<br>　　而每一分又有60秒,每一秒就代表1855.3m/60=30.92m
<br>
<br>　　任意两点距离计算公式为
<br>
<br>　　d＝111.12cos{1/[sin&#934;Asin&#934;B十cos&#934;Acos&#934;Bcos(&#955;B—&#955;A)]}
<br>
<br>　　其中A点经度，纬度分别为&#955;A和&#934;A，B点的经度、纬度分别为&#955;B和&#934;B，d为距离。</p>
<br>  <img src ="http://www.cppblog.com/Khan/aggbug/43390.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2008-02-28 15:18 <a href="http://www.cppblog.com/Khan/archive/2008/02/28/43390.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>技巧: 用 uniq 除去重复行(转载自ibm论坛)</title><link>http://www.cppblog.com/Khan/archive/2007/11/19/36921.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Mon, 19 Nov 2007 02:23:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/11/19/36921.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/36921.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/11/19/36921.html#Feedback</comments><slash:comments>1</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/36921.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/36921.html</trackback:ping><description><![CDATA[&nbsp;&nbsp;&nbsp; 重复行通常不会造成问题，但是有时候它们的确会引起问题。<br>&nbsp;&nbsp;&nbsp; 此时，不必花上一个下午的时间来为它们编制过滤器，uniq 命令便是唾手可得的好工具。了解一下它是如何节省您的时间和精力的。<br><br>进行排序之后，您会发现有些行是重复的。有时候该重复信息是不需要的，可以将它除去以节省磁盘空间。<br>不必对文本行进行排序，但是您应当记住 uniq 在读取行时会对它们进行比较并将只除去两个或更多的连续行。<br>下面的示例说明了它实际上是如何工作的：<br>清单 1. 用 uniq 除去重复行<br><br>&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $ cat happybirthday.txt<br>Happy Birthday to You!<br>Happy Birthday to You!<br>Happy Birthday Dear Tux!<br>Happy Birthday to You!<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $ sort happybirthday.txt <br>Happy Birthday Dear Tux!<br>Happy Birthday to You!<br>Happy Birthday to You!<br>Happy Birthday to You!<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $ sort happybirthday.txt | uniq<br>Happy Birthday Dear Tux!<br>Happy Birthday to You!<br><br><br><br>警告：请不要使用 <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; uniq 或任何其它工具从包含财务或其它重要数据的文件中除去重复行。<br>&nbsp;&nbsp;&nbsp; 在这种情况下，重复行几乎总是表示同一金额的另一个交易，将它除去会给会计部造成许多困难。千万别这么干！<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br><br>如果您希望您的工作轻松点，比如只显示唯一的或重复的行，那么该怎么办呢？您可以用 -u （唯一）和 -d （重复）选项来做到这一点，例如：<br>清单 2. 使用 -u 和 -d 选项<br>$ sort happybirthday.txt | uniq -u<br>Happy Birthday Dear Tux!<br>$ sort happybirthday.txt | uniq -d<br>Happy Birthday to You!<br><br><br>清单 3. 使用 -c 选项<br><br>&nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; &nbsp;&nbsp;&nbsp; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $ sort happybirthday.txt | uniq -uc<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 1 Happy Birthday Dear Tux!<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; $ sort happybirthday.txt | uniq -dc<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 3 Happy Birthday to You!<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br><br><br>就算 uniq 对完整的行进行比较，它仍然会很有用，但是那并非该命令的全部功能。特别方便的是：使用 -f 选项，<br>后面跟着要跳过的字段数，它能够跳过给定数目的字段。当您查看系统日志时这非常有用。<br>通常，某些项要被复制许多次，这使得查看日志很难。使用简单的 uniq 无法完成任务，因为每一项都以不同的时间戳记开头。<br>但是如果您告诉它跳过所有的时间字段，您的日志一下子就会变得更加便于管理。试一试 uniq -f 3 /var/log/messages ，亲眼看看。<br><br>还有另一个选项 -s ，它的功能就像 -f 一样，但是跳过给定数目的字符。您可以一起使用 -f 和 -s 。 <br>uniq 先跳过字段，再跳过字符。如果您只想使用一些预先设置的字符进行比较，那么该怎么办呢？试试看 -w 选项。<br><br><br><img src ="http://www.cppblog.com/Khan/aggbug/36921.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-11-19 10:23 <a href="http://www.cppblog.com/Khan/archive/2007/11/19/36921.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Gawk使用记录</title><link>http://www.cppblog.com/Khan/archive/2007/11/16/36752.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Fri, 16 Nov 2007 07:23:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/11/16/36752.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/36752.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/11/16/36752.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/36752.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/36752.html</trackback:ping><description><![CDATA[这是一个强大的处理格式化文本的工具,通过使用其脚本,几乎可以把文本当作数据库处理<br><br><br>分隔符为逗号, 标尺格式化显示各个字段<br>gawk&nbsp; -F"," "{printf \"%-6s %-9s %-9s %-9s %-9s\n\", NR, $1, $2, $4, $12}"&nbsp;&nbsp; aStockList.csv&nbsp; <br>如:<br>1&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 代码&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 名称&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 现价&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 今开&nbsp;&nbsp;&nbsp;&nbsp; <br>2&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000001&nbsp;&nbsp;&nbsp; 深发展Ａ&nbsp; 40.45&nbsp;&nbsp;&nbsp;&nbsp; 40.7&nbsp;&nbsp;&nbsp;&nbsp; <br>3&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000002&nbsp;&nbsp;&nbsp; 万&nbsp; 科Ａ&nbsp; 35.8&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 35.69&nbsp;&nbsp;&nbsp; <br>4&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000004&nbsp;&nbsp;&nbsp; ST 国 农&nbsp; 9.72&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 9.91&nbsp;&nbsp;&nbsp;&nbsp; <br>5&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000005&nbsp;&nbsp;&nbsp; ST 星 源&nbsp; 0&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ---&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br>6&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000006&nbsp;&nbsp;&nbsp; 深振业Ａ&nbsp; 33.3&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 33.31&nbsp;&nbsp;&nbsp; <br>7&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000007&nbsp;&nbsp;&nbsp; ST 达 声&nbsp; 7.18&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 7.1&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br>8&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000008&nbsp;&nbsp;&nbsp; *ST 宝投&nbsp; 0&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ---&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br>9&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000009&nbsp;&nbsp;&nbsp; S深宝安A&nbsp; 13.59&nbsp;&nbsp;&nbsp;&nbsp; 13.6&nbsp;&nbsp;&nbsp;&nbsp; <br>10&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000010&nbsp;&nbsp;&nbsp; S ST华新&nbsp; 0&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; ---&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br><br><br>取文件最后一行的行号.实际就是取总行数<br>gawk "END {print NR}"&nbsp; aStockList.csv&nbsp;&nbsp; <br><br><br><br>将数据分类汇总<br>gawk -F"," "{pos=(NR-1)%40; page=int((NR-1)/40); a=int((NR-1)/600) } <br>&nbsp;&nbsp;&nbsp; {print $1\",\",$2\",\",pos\",\",page\",\",a}"&nbsp; aStockList.csv |<br>&nbsp; gawk -F"," "BEGIN <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; { printf \"%-6s %-9s %-9s&nbsp; %-4s\n\", \"&nbsp; \", \"代码\", \"名称\", \"条/页/位置\"; <br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; print \"----------------------------------\"&nbsp; }<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; { printf\"%-6s %-9s %-9s %-4s \n\", NR, $1, $2, $5\"/\"$4%15\"/\"$3}"<br><br><br>原始数据:<br>代码&nbsp;&nbsp; ,名称,涨幅%%,现价,日涨跌,买入价,卖出价,总量,现量,涨速%%,换手%%,今开<br>000001,深发展Ａ,-0.32,40.45,-0.54,40.45,40.48,90119,32,0.24,0.58,40.7<br>000002,万&nbsp; 科Ａ,-0.56,35.8,-0.2,35.79,35.8,172067,3,0.56,0.33,35.69<br>000004,ST 国 农,-1.82,9.72,-0.18,9.7,9.72,18424,8,0,2.82,9.91<br>000005,ST 星 源,--- ,0,--- ,--- ,--- ,0,0,--- ,0,--- <br>000006,深振业Ａ,0,33.3,0,33.22,33.3,8753,6,0.27,0.4,33.31<br>000007,ST 达 声,2.43,7.18,0.17,7.15,7.18,11955,2,0.7,0.83,7.1<br>000008,*ST 宝投,--- ,0,--- ,--- ,--- ,0,0,--- ,0,--- <br>000009,S深宝安A,-1.02,13.59,-0.14,13.59,13.6,31747,150,0.22,0.55,13.6<br>000010,S ST华新,--- ,0,--- ,--- ,--- ,0,0,--- ,0,--- <br>000011,S深物业A,-0.86,12.65,-0.11,12.6,12.65,1608,24,0.39,0.18,12.43<br>000012,南&nbsp; 玻Ａ,0.17,18.16,0.03,18.16,18.18,32715,149,0.66,0.85,18<br>000014,沙河股份,--- ,0,--- ,--- ,--- ,0,0,--- ,0,--- <br>000016,深康佳Ａ,--- ,0,--- ,--- ,--- ,0,0,--- ,0,--- <br>000017,S ST中华,--- ,0,--- ,--- ,--- ,0,0,--- ,0,--- <br>000018,ST中冠Ａ,-0.39,7.66,-0.03,7.66,7.67,1182,2,0.13,0.28,7.69<br>000019,深深宝Ａ,-2.81,17.3,-0.5,17.3,17.38,12168,9,0.69,1.66,17.6<br>000020,ST华发Ａ,-0.14,6.91,-0.01,6.86,6.91,3235,6,0,0.5,6.91<br>000021,长城开发,-1.97,15.39,-0.31,15.38,15.39,18408,3,0.39,0.5,15.68<br>000022,深赤湾Ａ,-3.59,24.45,-0.91,24.45,24.46,5446,9,0.16,0.46,25.18<br>000023,深天地Ａ,-1.79,10.41,-0.19,10.4,10.41,3878,17,-0.19,0.58,10.78<br>000024,招商地产,-3.42,87.7,-3.11,87.71,87.99,2213,51,-0.11,0.07,91.9<br>000025,特&nbsp; 力Ａ,-1.48,13.99,-0.21,13.95,13.99,6856,4,-0.07,1.43,14.18<br>000026,飞亚达Ａ,-3.49,11.6,-0.42,11.6,11.65,20177,3,0.6,2.54,11.9<br>000027,深能源Ａ,-0.23,21.3,-0.05,21.28,21.3,30689,5,0.37,0.51,21.4<br>000028,一致药业,-1.35,15.38,-0.21,15.31,15.38,6399,3,0.32,0.57,15.58<br>000029,深深房Ａ,-1.21,7.36,-0.09,7.35,7.36,16261,7,1.51,0.6,7.49<br>000030,S*ST盛润,--- ,0,--- ,--- ,--- ,0,0,--- ,0,--- <br>000031,中粮地产,0.89,27.29,0.24,27.28,27.29,46135,78,0.25,0.94,27.05<br>000032,深桑达Ａ,-2.2,11.1,-0.25,11.07,11.1,5361,50,0.18,0.47,11.31<br>000033,新都酒店,-1.94,6.07,-0.12,6.06,6.07,19441,5,0.66,1.23,6.13<br>000034,SST 深泰,-0.48,8.24,-0.04,8.24,8.27,3797,15,0.12,0.45,8.21<br>000035,ST 科 健,--- ,0,--- ,--- ,--- ,0,0,--- ,0,--- <br>000036,华联控股,1.28,7.91,0.1,7.9,7.91,97065,300,0.5,1.26,7.73<br>000037,深南电Ａ,-1.9,8.25,-0.16,8.24,8.25,8874,62,0.24,0.55,8.4<br>000039,中集集团,-1.41,23.7,-0.34,23.7,23.72,55243,9,0.21,0.59,24.05<br>000040,深 鸿 基,-1.96,8.02,-0.16,8.01,8.02,24508,10,0.62,0.62,8.2<br>000042,深 长 城,-1.42,23.66,-0.34,23.66,23.7,3064,4,0.25,0.23,24.1<br>000043,深南光Ａ,1.83,23.9,0.43,23.85,23.9,1543,11,0.42,0.17,23.53<br>000045,深纺织Ａ,-1.88,7.31,-0.14,7.31,7.36,3779,5,-0.67,0.81,7.45<br>000046,泛海建设,-0.32,59.89,-0.19,59.89,59.9,4754,4,-0.01,0.21,60.11<br>000048,*ST 康达,-0.95,5.2,-0.05,5.2,5.22,11110,2,0,0.5,5.27<br>000049,德赛电池,2.26,10.86,0.24,10.85,10.86,8425,44,0.09,1.33,10.62<br>000050,深天马Ａ,-0.66,13.58,-0.09,13.56,13.58,10580,4,0.36,0.88,13.76<br>000055,方&nbsp; 大Ａ,-1.48,7.32,-0.11,7.32,7.33,7959,5,0.68,0.67,7.47<br>000056,深 国 商,-2.46,11.1,-0.28,11.12,11.19,5911,8,0.45,0.6,11.38<br>000058,*ST 赛格,-0.21,9.64,-0.02,9.63,9.64,25708,60,-0.41,1.22,9.87<br>000059,辽通化工,0.27,11.32,0.03,11.31,11.32,62685,28,0.17,1.9,11.32<br>000060,中金岭南,2.16,47.2,1,47.18,47.2,135188,3,1.17,3.13,46.19<br><br><br><br>目标数据:<br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 代码&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 名称&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 条/页/位置<br>----------------------------------<br>1&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000001&nbsp;&nbsp;&nbsp;&nbsp; 深发展Ａ&nbsp; 0/0/ 0 <br>2&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000002&nbsp;&nbsp;&nbsp;&nbsp; 万&nbsp; 科Ａ&nbsp; 0/0/ 1 <br>3&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000004&nbsp;&nbsp;&nbsp;&nbsp; ST 国 农&nbsp; 0/0/ 2 <br>4&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000005&nbsp;&nbsp;&nbsp;&nbsp; ST 星 源&nbsp; 0/0/ 3 <br>5&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000006&nbsp;&nbsp;&nbsp;&nbsp; 深振业Ａ&nbsp; 0/0/ 4 <br>6&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000007&nbsp;&nbsp;&nbsp;&nbsp; ST 达 声&nbsp; 0/0/ 5 <br>7&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000008&nbsp;&nbsp;&nbsp;&nbsp; *ST 宝投&nbsp; 0/0/ 6 <br>8&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000009&nbsp;&nbsp;&nbsp;&nbsp; S深宝安A&nbsp; 0/0/ 7 <br>9&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; 000010&nbsp;&nbsp;&nbsp;&nbsp; S ST华新&nbsp; 0/0/ 8 <br>10&nbsp;&nbsp;&nbsp;&nbsp; 000011&nbsp;&nbsp;&nbsp;&nbsp; S深物业A&nbsp; 0/0/ 9 <br>11&nbsp;&nbsp;&nbsp;&nbsp; 000012&nbsp;&nbsp;&nbsp;&nbsp; 南&nbsp; 玻Ａ&nbsp; 0/0/ 10 <br>12&nbsp;&nbsp;&nbsp;&nbsp; 000014&nbsp;&nbsp;&nbsp;&nbsp; 沙河股份&nbsp; 0/0/ 11 <br>13&nbsp;&nbsp;&nbsp;&nbsp; 000016&nbsp;&nbsp;&nbsp;&nbsp; 深康佳Ａ&nbsp; 0/0/ 12 <br>14&nbsp;&nbsp;&nbsp;&nbsp; 000017&nbsp;&nbsp;&nbsp;&nbsp; S ST中华&nbsp; 0/0/ 13 <br>15&nbsp;&nbsp;&nbsp;&nbsp; 000018&nbsp;&nbsp;&nbsp;&nbsp; ST中冠Ａ&nbsp; 0/0/ 14 <br>16&nbsp;&nbsp;&nbsp;&nbsp; 000019&nbsp;&nbsp;&nbsp;&nbsp; 深深宝Ａ&nbsp; 0/0/ 15 <br>17&nbsp;&nbsp;&nbsp;&nbsp; 000020&nbsp;&nbsp;&nbsp;&nbsp; ST华发Ａ&nbsp; 0/0/ 16 <br>18&nbsp;&nbsp;&nbsp;&nbsp; 000021&nbsp;&nbsp;&nbsp;&nbsp; 长城开发&nbsp; 0/0/ 17 <br>19&nbsp;&nbsp;&nbsp;&nbsp; 000022&nbsp;&nbsp;&nbsp;&nbsp; 深赤湾Ａ&nbsp; 0/0/ 18 <br>20&nbsp;&nbsp;&nbsp;&nbsp; 000023&nbsp;&nbsp;&nbsp;&nbsp; 深天地Ａ&nbsp; 0/0/ 19 <br>21&nbsp;&nbsp;&nbsp;&nbsp; 000024&nbsp;&nbsp;&nbsp;&nbsp; 招商地产&nbsp; 0/0/ 20 <br>22&nbsp;&nbsp;&nbsp;&nbsp; 000025&nbsp;&nbsp;&nbsp;&nbsp; 特&nbsp; 力Ａ&nbsp; 0/0/ 21 <br>23&nbsp;&nbsp;&nbsp;&nbsp; 000026&nbsp;&nbsp;&nbsp;&nbsp; 飞亚达Ａ&nbsp; 0/0/ 22 <br>24&nbsp;&nbsp;&nbsp;&nbsp; 000027&nbsp;&nbsp;&nbsp;&nbsp; 深能源Ａ&nbsp; 0/0/ 23 <br>25&nbsp;&nbsp;&nbsp;&nbsp; 000028&nbsp;&nbsp;&nbsp;&nbsp; 一致药业&nbsp; 0/0/ 24 <br>26&nbsp;&nbsp;&nbsp;&nbsp; 000029&nbsp;&nbsp;&nbsp;&nbsp; 深深房Ａ&nbsp; 0/0/ 25 <br>27&nbsp;&nbsp;&nbsp;&nbsp; 000030&nbsp;&nbsp;&nbsp;&nbsp; S*ST盛润&nbsp; 0/0/ 26 <br>28&nbsp;&nbsp;&nbsp;&nbsp; 000031&nbsp;&nbsp;&nbsp;&nbsp; 中粮地产&nbsp; 0/0/ 27 <br>29&nbsp;&nbsp;&nbsp;&nbsp; 000032&nbsp;&nbsp;&nbsp;&nbsp; 深桑达Ａ&nbsp; 0/0/ 28 <br>30&nbsp;&nbsp;&nbsp;&nbsp; 000033&nbsp;&nbsp;&nbsp;&nbsp; 新都酒店&nbsp; 0/0/ 29 <br>31&nbsp;&nbsp;&nbsp;&nbsp; 000034&nbsp;&nbsp;&nbsp;&nbsp; SST 深泰&nbsp; 0/0/ 30 <br>32&nbsp;&nbsp;&nbsp;&nbsp; 000035&nbsp;&nbsp;&nbsp;&nbsp; ST 科 健&nbsp; 0/0/ 31 <br>33&nbsp;&nbsp;&nbsp;&nbsp; 000036&nbsp;&nbsp;&nbsp;&nbsp; 华联控股&nbsp; 0/0/ 32 <br>34&nbsp;&nbsp;&nbsp;&nbsp; 000037&nbsp;&nbsp;&nbsp;&nbsp; 深南电Ａ&nbsp; 0/0/ 33 <br>35&nbsp;&nbsp;&nbsp;&nbsp; 000039&nbsp;&nbsp;&nbsp;&nbsp; 中集集团&nbsp; 0/0/ 34 <br>36&nbsp;&nbsp;&nbsp;&nbsp; 000040&nbsp;&nbsp;&nbsp;&nbsp; 深 鸿 基&nbsp; 0/0/ 35 <br>37&nbsp;&nbsp;&nbsp;&nbsp; 000042&nbsp;&nbsp;&nbsp;&nbsp; 深 长 城&nbsp; 0/0/ 36 <br>38&nbsp;&nbsp;&nbsp;&nbsp; 000043&nbsp;&nbsp;&nbsp;&nbsp; 深南光Ａ&nbsp; 0/0/ 37 <br>39&nbsp;&nbsp;&nbsp;&nbsp; 000045&nbsp;&nbsp;&nbsp;&nbsp; 深纺织Ａ&nbsp; 0/0/ 38 <br>40&nbsp;&nbsp;&nbsp;&nbsp; 000046&nbsp;&nbsp;&nbsp;&nbsp; 泛海建设&nbsp; 0/0/ 39 <br>41&nbsp;&nbsp;&nbsp;&nbsp; 000048&nbsp;&nbsp;&nbsp;&nbsp; *ST 康达&nbsp; 0/1/ 0 <br>42&nbsp;&nbsp;&nbsp;&nbsp; 000049&nbsp;&nbsp;&nbsp;&nbsp; 德赛电池&nbsp; 0/1/ 1 <br>43&nbsp;&nbsp;&nbsp;&nbsp; 000050&nbsp;&nbsp;&nbsp;&nbsp; 深天马Ａ&nbsp; 0/1/ 2 <br>44&nbsp;&nbsp;&nbsp;&nbsp; 000055&nbsp;&nbsp;&nbsp;&nbsp; 方&nbsp; 大Ａ&nbsp; 0/1/ 3 <br>45&nbsp;&nbsp;&nbsp;&nbsp; 000056&nbsp;&nbsp;&nbsp;&nbsp; 深 国 商&nbsp; 0/1/ 4 <br>46&nbsp;&nbsp;&nbsp;&nbsp; 000058&nbsp;&nbsp;&nbsp;&nbsp; *ST 赛格&nbsp; 0/1/ 5 <br>47&nbsp;&nbsp;&nbsp;&nbsp; 000059&nbsp;&nbsp;&nbsp;&nbsp; 辽通化工&nbsp; 0/1/ 6 <br>48&nbsp;&nbsp;&nbsp;&nbsp; 000060&nbsp;&nbsp;&nbsp;&nbsp; 中金岭南&nbsp; 0/1/ 7 <br>49&nbsp;&nbsp;&nbsp;&nbsp; 000061&nbsp;&nbsp;&nbsp;&nbsp; 农 产 品&nbsp; 0/1/ 8 <br>50&nbsp;&nbsp;&nbsp;&nbsp; 000062&nbsp;&nbsp;&nbsp;&nbsp; 深圳华强&nbsp; 0/1/ 9 <br>51&nbsp;&nbsp;&nbsp;&nbsp; 000063&nbsp;&nbsp;&nbsp;&nbsp; 中兴通讯&nbsp; 0/1/ 10 <br>52&nbsp;&nbsp;&nbsp;&nbsp; 000065&nbsp;&nbsp;&nbsp;&nbsp; 北方国际&nbsp; 0/1/ 11 <br> <img src ="http://www.cppblog.com/Khan/aggbug/36752.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-11-16 15:23 <a href="http://www.cppblog.com/Khan/archive/2007/11/16/36752.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>关于Linux裁剪(转载老鸨在Linuxsir发布的文章)</title><link>http://www.cppblog.com/Khan/archive/2007/11/09/36186.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Fri, 09 Nov 2007 03:32:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/11/09/36186.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/36186.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/11/09/36186.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/36186.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/36186.html</trackback:ping><description><![CDATA[<div id="post_message_683877" style="overflow-x: hidden;">项目基本结束，这个是其中系统裁减的一个总结文档，不知道有没有人感兴趣：)<br><br>=============================================<br><br>前言:<br>为了完成用户的需求，需制作一个完整的环境供AP运行，且存在一些约束条件。<br><br>关键字：<br>DOM
Kernel Busybox X-Window Window-Manager Interbase nvidia
cutdown<br><br>目标说明：<br>在一个64M的DOM(Disk on
module)上建立可以运行完整的AP的环境<br><br>约束条件：<br>1、可利用的总空间为64M，由DOM提供，但实际可用空间只有53-59M，原因可能与设备文件和DOM本身有关，未确定<br>2、显卡为nvidia系列<br>3、kernel选用2.4.20，没有使用redhat自带的版本。采集卡的Driver目前还只能在2.4.20的kernel下编译，由于其移植性较差，已经开始考虑重新整理成可适合kernelversion大于2.4.25的所有kernel，参考bttv的最新实现<br>4、数据库选用interbase系列，目前使用的为firebird-1.5(firebird为interbase的开源实现，接口和interbase基本相同)。<br>5、其他附属的功能要求，在后面的文档中会有说明<br><br>制作流程：<br>某些部分的原理和实现没有办法写的很全面，但基本上会提供一些url的连接，供相关人员参考。基本上按照制作流程来写，前后相互牵连的部分不做特别说明。<br><br>一、Kernel的选择和编译：<br>由于driver的缘故，只能使用2.4.20的kernel。2.4.20和2.4.25都有对Driver做过尝试，其他版本的kernel没有试过，应该是可以的，尚未确认。在2.6的kernel上无法编译，目前确定的原因是makefile有问题，估计做一些相应的修改还是可以的，可参考bttv的makefile(<a  href="http://linux.bytesex.org/v4l2/bttv.html" target="_blank">http://linux.bytesex.org/v4l2/bttv.html</a>)。<br>回到kernel上来，基本上的编译原则是尽量减去不需要的部分，以及除了一些需要临时加载的Driver尽量不要出现module。由于上面所说的理由，DOM中使用的kernel为原始的2.4.20，可以从<a  href="http://www.kernel.org/" target="_blank">http://www.kernel.org</a>下载，本文档的附加文件里也可以找到。<br>另外，由于需求的定义，系统启动时需要显示splash画面，所以kernel还需要加入bootsplash功能，这个功能是第三方提供的，作为补丁加入kernel。作法如下：<br><br>1、打内核补丁并编译内核<br>假设内核源文件安装在/usr/src/linux/。下载bootsplash
3.07(地址：<a  href="ftp://ftp.suse.com/" target="_blank">ftp://ftp.suse.com</a>)，然后：<br><br>yourbox:~ # cd
/usr/src/linux<br>yourbox:/usr/src/linux # patch -p1 &lt;
/path/to/bootsplash-3.0.7-2.4.20-vanilla.diff<br>yourbox:/usr/src/linux
#<br><br>配置内核，如make menuconfig或make xconfig，在&#8221;Console drivers&#8221; -&gt;
&#8220;Frame-Buffer support&#8221; 选择 &#8220;VESA VGA graphics console&#8221; 或其他与你的显卡相应的驱动。打开 &#8220;Use
splash screen instead of boot logo&#8221;. 在 &#8220;Block Devices&#8221;中打开&#8221;Initial Ramdisk
support&#8221;，保存配置并编译内核，将生成的内核拷到/boot
下，并修改lilo或grub的配置文件以使用新的内核来启动。<br><br>2、加入图片<br>下载并安装splash工具：<a  href="ftp://ftp.suse.com/pub/people/" target="_blank">ftp://ftp.suse.com/pub/people/</a><br><br># cd ~/splash<br># tar
xvjf
splashutils.tar.bz2<br>splashutils/<br>splashutils/Makefile<br>splashutils/splash.c<br>[..]<br>splashutils/ChangeLog<br>splashutils/COPYING<br>#
cd splashutils<br># make splash<br>gcc -Os -Wall -c -o splash.o splash.c gcc -Os
-Wall -o splash splash.o<br>strip splash<br># cp splash /sbin/<br># cd
..<br><br>将图片及相关的信息加入到initrd中去:<br>/sbin/splash -s -f
/etc/bootsplash/themes/yourtheme/config/bootsplash-1024x768.cfg &gt;&gt;
/boot/initrd.splash<br><br>图片在附件文件中<br><br>3、运行lilo更新配置文件(grub就不用更新了)，重新启动，如果一切正常，就可以看到启动画面了。同时会有这样一些信息：<br><br>vesafb:
framebuffer at 0xf0000000, mapped to 0xdc816000, size 65472k vesafb: mode is
1024x768x16, linelength=2048, pages=41 vesafb: protected mode interface info at
c000:5137 vesafb: scrolling: redraw<br>vesafb: directcolor: size=0:5:6:5,
shift=0:11:5:0 Looking for splash picture.... silenjpeg size 11165 bytes, found
(1024x768, 4912 bytes, v3) Got silent
jpeg.<br><br>kernel的config文件比较大，在附件中有，这里就不列举了。<br><br>编译过程：<br>1、获取2.4.20的原始kernel压缩包(linux-2.4.20.tar.bz2)
<br>2、tar xvjpf linux-2.4.20.tar.bz2<br>3、cp config-2.4.20
(kernelsource)/.config #拷贝config-2.4.20到kernel
source所在目录中并以.config为新的文件名<br>4、cd (kernelsource)<br>5、make menuconfig
#不需要做任何改动，直接退出 <br>6、make dep &amp;&amp; make bzImage &amp;&amp; make modules
&amp;&amp; make modules_install &amp;&amp; make install
<br>7、如果没有问题，继续下一步，如果有问题，请检查编译环境是否正确，并重复step 6
<br>8、此时kernel已经编译完毕，需要做两件事情，一是保存将来放入DOM的文件，二是将当前的发行版的kernel换成2.4.20，以便后面的nvidia显卡dirver的正确编译。
<br>9、创建一个保存目录，比如~/kernelbackup <br>10、cp (kernelsource)/arch/i386/boot/bzImage
~/kernelbackup # 保存kernel <br>11、cp /lib/modules/2.4.20 ~/kernelbackup/ -arf #
保存编译出的所有modules
<br>12、如果当前的发行版使用的是grub，则修改/boot/grub/grub.conf(如果没有这个文件可以修改/boot/grub/menu.lst，都是一样的)，如果是lilo，修改/etc/lilo.conf。下面是grub的修改说明，lilo的修改办法可以参考相关文档：<br><br>#
add below to your grub.conf<br>title new kernel(2.4.20) # title just, u can
modify it anywhere<br>root (hd0,0) # root setup<br>kernel
(hd0,0)/boot/bzImage-2.4.20 ro root=/dev/hda1 vga=791 splash=silent #
just.....<br>initrd (hd0,0)/boot/initrd.splash # splash that show when booting
of
OS<br><br>13、reboot<br>14、选择新的启动选项，检查是否正确<br><br>二、Shell的选择和编译:<br>到目前为止，kernel的裁减基本上结束，下面是shell的选择和编译。
对于linux而言，kernel只是提供系统调用接口，本身无法直接使用，需要外部shell的支持。一般shell有几种选择，如bash、ash、busybox等，由于busybox相对尺寸最小，而且提供了基本完整的功能，所以选择busybox做为系统的shell。详细信息参阅<a  href="http://www.busybox.net/" target="_blank">www.busybox.net</a>，附件中有目前使用的busybox版本。busybox的流程主要是编译和安装，从而联合kernel组成一个基本系统。
busybox的配置文件在附件中有，这里就不列举了。<br><br>编译过程:<br>和kernel基本相似<br>1、解压busybox<br>2、复制config到busybox源码目录下<br>3、make
menuconfig #不做改动即可退出<br>4、make dep &amp;&amp;
make<br><br>三、基本系统的安装：<br>到此时，busybox和kernel都已经准备完毕，接下来需要一个分区来安装他们。
不管是使用一个单独的分区还是完整的DOM都可以，但总归需要一个完整的目标分区供使用。假设目标分区为/dev/hdc1，下面的说明会以此为基准。
需要说明的一点是，一开始尽量不要用DOM直接调试，因为其速度和容量都十分的不好，会造成调试的困难，直到调试后期再使用是个比较不错的主意。<br><br>现在进入基本系统的组装:<br>#
fdisk /dev/hdc1 and format it with ext2 or ext3. My suggest is ext3.<br>Mount
/dev/hdc1 /mnt/dom # mount目标分区 <br>mkdir /mnt/dom/boot<br>mkdir
/mnt/dom/boot/grub<br>cp (kernelbackup)/bzImage /mnt/dom/boot # copy kernel to
dom<br>cp (kernelbackup)/initrd.splash /mnt/dom/boot # copy initrd splash to dom
<br>mkdir /mnt/dom/lib<br>mkdir /mnt/dom/lib/modules<br>cp (kernelbackup)/2.4.20
/mnt/dom/lib/modules -arf # copy all modules to dom cd (busyboxpath)<br>make
PREFIX=/mnt/dom install # install busybox to dom<br>现在，一个基本系统基本安装完毕，接下来是配置问题：
<br>mkdir /mnt/dom/etc # all config here<br>mkdir /mnt/dom/dev # device
file<br>mkdir /mnt/dom/mnt<br>mkdir /mnt/dom/proc<br>mkdir /mnt/dom/tmp<br>mkdir
/mnt/dom/var<br>mkdir /mnt/dom/lib<br>mkdir /mnt/dom/root # home of
root<br>mkdir /mnt/dom/usr # X window-manager lib, etc <br>cp
(busyboxpath)/examples/bootfloppy/etc/* /mnt/dom/etc -arf # base config <br>cp
/dev/* /mnt/dom/dev -arf # device file. Will cutdown part of
all<br><br>下面是加入必需的连接库：<br>1、ldd
busybox<br>2、查看busybox使用了哪些连接库，拷贝至目标分区中同样的路径下，一般为/lib
<br>3、再用ldd查看连接库是否还有需要的库文件，如果有同样拷贝到目标分区中 <br>4、重复第三步<br>5、cp /dev/*
/mnt/dom/dev/ -arf # 后期还会做一些裁减<br>Grub配置：<br># add below to your
grub.conf<br>title new kernel(2.4.20) # title just, u can modify it
anywhere<br>root (hd0,0) # root setup<br>kernel (hd0,0)/boot/bzImage-2.4.20 ro
root=/dev/hda1 vga=791 splash=silent # just.....<br>initrd
(hd0,0)/boot/initrd.splash # splash that show when booting of
OS<br><br>现在可以做一些测试，看看基本系统是否工作正常。执行下面的命令 <br>cd /mnt<br>mkdir dom<br>mount
/dev/hdc1 dom # mount it<br>chroot /mnt/dom
/bin/sh<br>如果你看到登陆成功的信息就表示基本系统没有什么问题了。<br><br>重新启动机器，并选择新的启动选项，看看基本系统是否正常，如果有问题，重新检查前面的步骤是否做的有问题。如果启动正常，那么，基本系统就基本完备，可以继续后面的步骤了。<br><br>四、Xfree86的裁减和安装：<br>基本系统已经正常工作，接下来就是xfree86的裁减和安装，首先切换到目标分区并确定系统处于正常工作状态。<br>在这里需要说明一下Linux的目录分布和作用情况。首先通过&#8220;ls
/&#8221;列举一下根分区，大致会有以下目录：<br>bin boot dev etc home lib mnt opt proc root sbin tmp usr
var <br>下面逐一说明：<br>bin: shell的工作目录，比如sh、bash、mount等命令 <br>boot:
kernel、ramdisk文件以及grub(lilo)的存放目录，有的发行版会为此目录单独创建一个分区，以防止系统崩溃的影响。在DOM中是不考虑的。
<br>dev:
所有的设备文件都存放在这里，比如/dev/video0、/dev/hda等。全部设备文件大概要占用400K左右的空间，但似乎全部拷贝过来的话，DOM总是会报空间不足，但实际还是有空间的，原因不明。目前的做法是对设备文件做了一些调整，去除了不需要的部分，参考后面的文件列表。
<br>etc:
Ap配置以及系统配置存放目录<br>home:普通用户的工作目录根<br>lib:基本库存放目录<br>mnt:mount<br>opt:看情形，目前是用做存放firebird<br>proc:系统工作所需的目录<br>root:一般为root的工作目录，可以调换<br>sbin:常规命令存放目录<br>tmp:一般为临时目录<br>usr:所有扩展命令和xfree86，以及window-manager所在目录，是系统最大的一个目录，包含内容最多。对于DOM来说，主要是存放连接库、xfree86、字体、window-manager等。<br>Var:临时目录，一般在发行版中为存放website文件、安装文件以及一些log信息等，在DOM中只作为临时目录使用<br><br>大致的分布情况说明完毕，接下来就是具体的裁减工作了。
实际上，xfree86有一些替代实现，比如freedesktop、fb等，甚至framebuffer也是一个可以考虑的方向，但是由于AP使用了nvidia显卡提供的opengl
1.3接口，导致目前的唯一选择就是xfree86。也许有其他更小的实现，希望能在以后改进。
进入正题，xfree86的主程序实际上就是一个XFree86，位于/usr/X11R6/bin，有的发行版下X是一个指向XFree86的连接，有的却是一个完整的程序，但不管怎么样，Xfree86就是最主要的程序。现在，在目标分区上mount发行版，以便可以拷贝我们所需要的：
<br>cd /mnt<br>mkdir dist # create mount path of distribute <br>mount /dev/hda1
dist # /dev/hda1 is root partition of your distribute. Check
it.<br>现在/mnt/dist就是发行版所在的位置。<br><br>mkdir /usr/X11R6<br>mkdir
/usr/X11R6/bin<br>mkdir /usr/lib<br>mkdir /usr/X11R6/lib<br>创建一些需要的目录。<br><br>cp
/mnt/dist/usr/X11R6/bin/XFree86 /usr/X11R6/bin -arf 拷贝xfree86的主程序。<br>cp
/mnt/dist/usr/bin/ldd /sbin # copy ldd that is used to cutdown
<br>ldd是用来在DOM的环境中做裁减工作的，直接输入ldd看看是否可以运行，如果执行有问题，一般是相关的连接库不全，按照之前的方法复制过来就可以了。
<br><br>现在，要查看XFree86需要哪些连接库和配置文件，以保证其可以运行起来。 <br>cd /usr/X11R6/bin<br>ldd
Xfree86<br>此时会看到很多的连接库，那么就需要把这些库全部从发行版上复制过来，可以直接复制到相对应的目录下，比如/usr/lib/或者/usr/X11R6/lib/下，需要注意的一点是，有些库本身还会需要其他的库，可以一层层的ldd出来，网络中有人做过自动工作的工具，但还是手动裁减比较可靠。全部的库导入完毕后，尝试运行/usr/X11R6/bin/XFree86，会看到一些出错信息，提示/etc/X11/XF86Config不存在，那么就将发行版中的/etc/X11目录全部复制到目标分区中：<br>cp
/mnt/dist/etc/X11 /etc
-arf<br>实际上这个目录中不是全部都需要的，某些部分是可以删除的，但我没有具体实验，而且尺寸并不是很大，就全部使用了。<br>现在再执行/usr/X11R6/bin/XFree86，会提示一些库没有找到，但实际上之前已经全部复制过来了，原因是从shell执行一条命令的时候，命令所需要的库是从以下的途径得到的：<br>1、搜索/lib<br>2、搜索/etc/ld.so.cache<br>之前所复制的库文件大半是放在/usr/lib和/usr/X11R6/lib下的，而且现在的/etc下还没有ld.so.cache文件，要生成这个文件就需要ldconfig这个命令：<br>cp
/mnt/dist/sbin/ldconfig /sbin
-arf<br>现在ldconfig是有了，但还需要与之有关的配置文件/etc/ld.so.conf，所以： <br>vi
/etc/ld.so.conf<br>/usr/lib<br>/usr/X11R6/lib<br>现在执行ldconfig，就会在/etc/下出现一个ld.so.cache。以后如果有新加入的库文件，而且不是存放在/lib/下的，都按照这个步骤来导入。现在，执行/usr/X11R6/bin/XFree86，出现的错误提示为无法打开/var/kdb和/var/log。<br>这里需要说明配置上的一个修改，cat
/etc/fstab，会看到现在的fstab只有一句话: <br>none /proc proc defaults 0 0
<br>现在要加入一些新的配置，新的fstab如下： <br>proc /proc proc defaults 0 0<br>none /var tmpfs
defaults 0 0<br>none /tmp tmpfs defaults 0 0<br>none /dev/pts devpts
gid=5,mode=620 0 0 <br>none /data tmpfs defaults 0
0<br>现在/var、/tmp和/data都是在内存中了，其中/data是将来mount磁盘的地方，需要手动mkdir出来：<br>mkdir
/data<br>现在修改/etc/init.d/rcS:<br>#! /bin/sh<br><br>/bin/mount -a<br><br>mkdir
/var/log<br>mkdir /var/lib<br>mkdir
/var/lib/xkb<br><br>重启DOM，现在应该存在/var/log、/var/lib、/var/xkb目录了，当然这些目录只是存放在内存中，所以需要每次启动时临时创建。<br>再运行XFree86，应该会看到一个错误的提示，说明还需要opengl的一些连接库，从发行版中复制出来就可以了。<br>尝试在目标分区中执行/usr/X11R6/bin/XFree86，如果没有进入X界面，需要检查之前的步骤是否有没有做对的地方。<br><br>五、Window-Manager的选择安装：<br>到目前为止，X已经完全移植到DOM中了，但一个包含基本系统和X的系统还不能满足AP的要求，接下来是Window-manager的选择和安装。<br>kde和gnome是无法安装到DOM中的，尺寸太大，可能的选择包括twm、fluxbox、windowmaker、icewm等，但需要满足以下几个条件：<br>1、有caption，而且Modal
dialog不能被切到后台，以符合用户的操作习惯<br>2、X上不能有任何多余的部分，即除了AP，不存在任何UI，如taskbar之类
<br>3、尺寸要小<br>4、最好不要有system menu和system buttons
<br><br>经过挑选，最终选择了fluxbox作为DOM的window-manager，尺寸相对其他window
manager要大一些(10M)，但是较好的满足了以上条件。<br><br>安装过程：<br>1、下载fluxbox<br>2、./configure<br>3、make<br>4、make
install<br>5、复制相关文件到DOM的相同目录中<br>6、测试，如果有问题，重复第一步<br>等window
manager安装完毕后，一个包含基本系统和window的环境就创建成功了。接下来就是一些附属部件的裁减和安装了。<br><br>六、其他部件的裁减和安装：<br>先切换到发行版。最后定义的数据库引擎为Firebird
1.5，所以先下载firebird 1.5(<a  href="http://prdownloads.sourceforge.net/firebird/FirebirdCS-1.5.0.4290-0.i686.tar.gz" target="_blank">http://prdownloads.sourceforge.net/f...-0.i686.tar.gz</a>)，然后在发行版上先安装。firebird会安装在/opt目录下，将/opt/firebird复制到目标分区中：<br>cp
/opt/firebird /mnt/dom/opt -arf<br><br>然后修改配置文件：<br>vi
/mnt/dom/etc/init.d/rcS<br>#! /bin/sh<br><br>/bin/mount -a<br><br>mkdir
/var/log<br>mkdir /var/lib<br>mkdir
/var/lib/xkb<br><br>/opt/firebird/bin/fb_lock_mgr
&amp;<br>/opt/firebird/bin/fb_inet_server
&amp;<br><br>现在切换到目标分区中，会看到进程列表中有一个fb_lock_mgr，这说明firebird已经安装成功。<br><br>由于实际的裁减过程中会遇到各种各样的问题，有些方面牵涉太广，以至没有办法单独说明，所以接下来是一些可能会遇到的问题说明：<br>1、nvidia的驱动需要先在发行版上解开，再执行make
&amp;&amp; make install &gt; install，然后修改install中的目标路径以将相关文件安装到DOM上，比如cp
libGL.so /usr/lib改为cp libGL.so
/mnt/dom/usr/lib。具体操作就不列举了。<br>2、busybox的mount有问题，不能mount -o
loop，所以cramfs的文件需要用发行版的mount，所以在dom的/mnt/cramfs目录下有一个mount，而/bin也有一个mount<br>3、为了便于调试，在dom中加入了telnet
server和ftp
client，分别使用的是utelnetd和cmdftp，出处可以通过google搜索<br>4、grub的安装使用grub-install即可<br>5、由于firebird等模块至少需要一个root用户，而busybox缺省是没有用户的，所以需要在/etc下复制两个文件：shadow和passwd<br>6、dhcp
client使用的是udhcpc<br>7、字体主要和以下目录有关：/usr/lib/gconv、/usr/lib/locale、/usr/X11R6/lib/X11/font和/usr/X11R6/lib/X11/locale(限于redhat，其他发行版会有一些差异，但具体内容是一样的)<br>8、硬件自检使用的是hwsetup，并对源代码做过一些修改，只保留了audio和network
card的检测，在附件里有原始和修改过的两个版本，可以对比参考<br>9、web
site功能是用kylix自己实现的，没有使用apache<br>10、由于dom的空间不足以摊平所有文件，所以/usr下面的文件全部都是以一个cramfs文件的格式出现的，参看后面的文件列表。<br><br>七、DOM的最后安装和打包：<br>cramfs文件的创建:<br>1、确定目标分区的可运行<br>2、确定/mnt/dom/usr/目录下的文件完整性<br>3、mkcramfs
/mnt/usr.cramfs /mnt/dom/usr # make a cramfs file of usr
path<br>4、保存/mnt/dom下的完整列表，以备将来的修改<br>5、rm /mnt/dom/usr/* -rf<br>6、mkdir
/mnt/dom/mnt/cramfs<br>7、cp /mnt/usr.cramfs /mnt/dom/mnt/cramfs<br>8、cp
/bin/mount /mnt/dom/mnt/cramfs -arf<br>9、add
/mnt/dom/etc/init.d/rcS:/mnt/cramfs/mount -o loop -t cramfs
/mnt/cramfs/usr.cramfs
/usr<br><br>现在，/mnt/dom目录下就已经是一个除了grub全部都是完整的DOM镜像了。那么最后要将这个镜像导入真实的DOM之中：<br>mkdir
/mnt/realdom<br>mount /dev/hdc1 /mnt/realdom # assume /dev/hdc1 is real
dom<br>cp /mnt/dom/* /mnt/realdom/
-arf<br>sync<br>此时DOM中已经有了一个完整的镜像，但还没有grub，那么执行：<br>grub-install
/dev/hdc1<br>重新启动，并在BOIS中选择真正的DOM，确认DOM的启动没有问题。重新切换到发行版，开始做DOM的镜像文件：<br>dd
if=/dev/hdc of=domfs # domfs is image of
dom<br>保存好这个名字为domfs的镜像文件，这就是一个可安装的包，安装到其他DOM中时，输入：<br>dd if=domfs
of=/dev/hdc<br>到目前为止，所有的流程都走了一遍，剩下的就是不断的实践和验证了。<br><br>后记：<br>经过一次完整的裁减过程，很自然的对Linux的整体结构和方式有了很清晰的了解，虽然不能对kernel有深入了解，但是起码为以后kernel方面的学习打下了很好的基础。由于牵涉方面比较多和杂，有些部分只能是实践过后才能知道其中的诀窍，当然大体的过程是一样的。<br><br>2004-06-01<br>cyantree<br><br><br><br>附录：<br>DOM文件列表：<br>略</div>
<!-- / message --><!-- edit note --><img src ="http://www.cppblog.com/Khan/aggbug/36186.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-11-09 11:32 <a href="http://www.cppblog.com/Khan/archive/2007/11/09/36186.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Symbian s60 app初步研究</title><link>http://www.cppblog.com/Khan/archive/2007/10/19/34621.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Fri, 19 Oct 2007 09:04:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/10/19/34621.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/34621.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/10/19/34621.html#Feedback</comments><slash:comments>2</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/34621.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/34621.html</trackback:ping><description><![CDATA[CApaApplication 类实现两个接口 NewApplication 和 E32Dll<br><br>整个程序的入口就是 NewApplication&nbsp; , <br>启动顺序 NewApplication&nbsp; --&gt;　New CAknApplication -&gt; New CApaDocument <br>Document -&gt; CreateAppUiL 启动APPUI <br>appui装入一个view 然后进入消息响应模块<br><br><br>UI程序的panel图标和list图标的名称固定为context_pane_icon.bmp list_icon.bmp, mask图标名称固定为context_pane_icon_mask.bmp, list_icon_mask.bmp , 名称不能够自定义, 不能错..否则会显示不出图标.. <br><br><br> <img src ="http://www.cppblog.com/Khan/aggbug/34621.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-10-19 17:04 <a href="http://www.cppblog.com/Khan/archive/2007/10/19/34621.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>RSA加密 版本1.5(RFC2313)</title><link>http://www.cppblog.com/Khan/archive/2007/05/17/24282.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 17 May 2007 05:54:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/05/17/24282.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/24282.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/05/17/24282.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/24282.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/24282.html</trackback:ping><description><![CDATA[<pre>组织：中国互动出版网（http://www.china-pub.com/）<br>RFC文档中文翻译计划（http://www.china-pub.com/compters/emook/aboutemook.htm）<br>E-mail：ouyang@china-pub.com<br>译者：徐孜骏（happygogo    happygogo@sina.com）<br>译文发布时间：2001-7-14<br>版权：本中文翻译文档版权归中国互动出版网所有。可以用于非商业用途自由转载，但必须<br>保留本文档的翻译及版权信息。<br><br><br>Network Working Group                                      B. Kaliski<br>Request for Comments: 2313                      RSA Laboratories East<br>Category: Informational                                    March 1998<br><br>                PKCS#1：RSA加密 版本1.5<br><br>本备忘录的状态<br>本备忘录为Internet社区提供了信息。它没有讲述任何一种Internet标准.本备忘录的发<br>布不受任何限制。<br>版权声明<br>Copyright (C) The Internet Society (1998).  保留所有权利。<br>略读<br>此篇文章描述了如何使用RSA公钥密码体系加密数据。<br>目录<br>1、范围	2<br>2、参考	2<br>3、定义	4<br>4、标志和缩写	5<br>5、总的概述	5<br>6、密钥生成	5<br>7、密钥语法	6<br>7．1公钥语法	6<br>7．2私钥语法	6<br>8、加密过程	7<br>8．1加密块格式化	7<br>8．2 8位字节串到整数的转换	8<br>8．3 RSA计算	8<br>8．4 整数到字节串的转换	9<br>9、解密过程	9<br>9．1 字节串到整数的转换	9<br>9．2  RSA计算	9<br>9．3 整数到字节串的转换	9<br>9．4 需加密块解析	10<br>10、签名算法	10<br>10．1 签名过程	10<br>10．2 验证过程	12<br>11、对象标识符	13<br>安全考虑	14<br>修订版记录	14<br>鸣谢	14<br>作者地址	14<br>版权声明	15<br><br>1、范围<br>此篇文档描述了如何使用RSA公钥密码体系加密数据。这将被用作数字签名和数字信<br>封，且在PKCS#7中有描述：<br>?	数字签名：签名内容首先被消息散列算法（如MD5）缩减成一个消息散列，然后<br>使用签名者的RSA私钥加密含有消息散列的字符串。原文和被加密的消息散列一<br>起组成符合PKCS #7中语法的数字签名。这种应用和PEM是兼容的。<br>?	数字信封：首先将被加信封的内容使用一个内容加密算法（例如DES）的内容加<br>密密钥加密，然后使用收件人的RSA公钥加密内容加密密钥。那个被加密内容和<br>被加密的密钥一起组成符合PKCS #7中语法的数字信封。这种应用和PEM是兼<br>容的。<br>此篇文档还描述了有关一个RSA公钥和私钥的语法。公钥语法被用于证书；私钥语法<br>被用于PKCS#8中的私钥信息。公钥语法在X.509和PEM是完全相同的。这样X.509/PEM <br>RSA密钥能被用于此篇文当中。<br>此篇文档还定义了三个签名算法，它们被用于签署X.509/PEM证书和CRL，PKCS#6<br>扩展证书，和其他使用数字签名的对象（例如X.401消息标记）。<br>有关消息散列和内容加密算法的细节并不属于此篇文档的范围，并且有关被文档要求<br>的假随机位的来源也不在此文档范围中。<br><br>2、参考<br>   FIPS PUB 46-1  National Bureau of Standards. FIPS PUB 46-1:<br>             Data Encryption Standard. January 1988.<br><br>   PKCS #6   RSA Laboratories. PKCS #6: Extended-Certificate<br>             Syntax. Version 1.5, November 1993.<br><br>   PKCS #7   RSA Laboratories. PKCS #7: Cryptographic Message<br>             Syntax. Version 1.5, November 1993.<br><br>   PKCS #8   RSA Laboratories. PKCS #8: Private-Key Information<br>             Syntax. Version 1.2, November 1993.<br><br>   RFC 1319  Kaliski, B., "The MD2 Message-Digest<br>             Algorithm," RFC 1319, April 1992.<br><br>   RFC 1320  Rivest, R., "The MD4 Message-Digest<br>             Algorithm," RFC 1320, April 1992.<br><br>   RFC 1321  Rivest, R., "The MD5 Message-Digest<br>             Algorithm," RFC 1321, April 1992.<br><br>   RFC 1423  Balenson, D., "Privacy Enhancement for<br>             Internet Electronic Mail: Part III: Algorithms,<br>             Modes, and Identifiers," RFC 1423, February 1993.<br><br>   X.208     CCITT. Recommendation X.208: Specification of<br>             Abstract Syntax Notation One (ASN.1). 1988.<br><br>   X.209     CCITT. Recommendation X.209: Specification of<br>             Basic Encoding Rules for Abstract Syntax Notation<br>             One (ASN.1). 1988.<br><br>   X.411     CCITT. Recommendation X.411: Message Handling<br>             Systems: Message Transfer System: Abstract Service<br>             Definition and Procedures.1988.<br><br>   X.509     CCITT. Recommendation X.509: The Directory--<br>             Authentication Framework. 1988.<br><br>   [dBB92]   B. den Boer and A. Bosselaers. An attack on the<br>             last two rounds of MD4. In J. Feigenbaum, editor,<br>             Advances in Cryptology---CRYPTO '91 Proceedings,<br>             volume 576 of Lecture Notes in Computer Science,<br>             pages 194-203. Springer-Verlag, New York, 1992.<br><br>   [dBB93]   B. den Boer  and A. Bosselaers. Collisions for the<br>             compression function of MD5. Presented at<br>             EUROCRYPT '93 (Lofthus, Norway, May 24-27, 1993).<br><br>   [DO86]    Y. Desmedt and A.M. Odlyzko. A chosen text attack<br>             on the RSA cryptosystem and some discrete<br>             logarithm schemes. In H.C. Williams, editor,<br>             Advances in Cryptology---CRYPTO '85 Proceedings,<br>             volume 218 of Lecture Notes in Computer Science,<br>             pages 516-521. Springer-Verlag, New York, 1986.<br><br>   [Has88]   Johan Hastad. Solving simultaneous modular<br>             equations. SIAM Journal on Computing,<br>             17(2):336-341, April 1988.<br><br>   [IM90]    Colin I'Anson and Chris Mitchell. Security defects<br>             in CCITT Recommendation X.509--The directory<br>             authentication framework. Computer Communications<br>             Review, :30-34, April 1990.<br><br>   [Mer90]   R.C. Merkle. Note on MD4. Unpublished manuscript,<br>             1990.<br><br>   [Mil76]   G.L. Miller. Riemann's hypothesis and tests for<br>             primality. Journal of Computer and Systems<br>             Sciences, 13(3):300-307, 1976.<br><br>   [QC82]    J.-J. Quisquater and C. Couvreur. Fast<br>             decipherment algorithm for RSA public-key<br>             cryptosystem. Electronics Letters, 18(21):905-907,<br>             October 1982.<br><br>   [RSA78]   R.L. Rivest, A. Shamir, and L. Adleman. A method<br>             for obtaining digital signatures and public-key<br>             cryptosystems. Communications of the ACM,<br>             21(2):120-126, February 1978.<br><br>3、定义<br>由于此篇文档的目的，下列定义将被使用。<br>算法标识符：通过对象标识符定义一种算法和相关参数的类型，此类型被定义在X.509<br>中。<br>ASN.1：抽象语法标记1，定义在X.208中。<br>BER：基础编码规则，定义在X.209中。<br>DES：数据加密标准，定义在FIPS PUB 46-1中。<br>MD2：RSA Data Security, Inc.的MD2消息散列算法，定义在RFC 1319中。<br>MD4：RSA Data Security, Inc.的MD4消息散列算法，定义在RFC 1320中。<br>MD5：RSA Data Security, Inc.的MD5消息散列算法，定义在RFC 1321中。<br>Modulus（模数）：由两个素数形成的整数。<br>PEM：因特网私人加密邮件，定义在RFC 1423和相关文当中。<br>RSA：RSA公钥密码体系，定义在[RSA78]中。<br>私人密钥：模数和私人指数。<br>公开密钥：模数和公开指数。<br><br>4、标志和缩写<br>大写标志（例如BT）表示字符串和位串（就签名S而言），小写标志（例如c）表示<br>整数。<br>   ab   16进制8位组值         c    指数<br>   BT   块类型                 d    私人指数<br>   D    数据                   e    公开指数<br>   EB   需加密块               k    模数的8位组长度                                <br>   ED   被加密的数据           n    模数<br>   M    消息                   p, q  模数的素数组成<br>   MD   消息散列              x    整数需加密块<br>   MD'  比较的消息散列         y    整数被加密数据<br>   PS   填充字符串             mod n  模 n<br>   S    签名                   X || Y  X，Y的级连<br>   ||X||  X字节长<br><br>5、总的概述<br>下面的六个章节详细的叙述了密钥生成，密钥语法，加密过程，解密过程，签名算法<br>和对象标识符。每个实体都要生成一对密钥：公钥和私钥。加密过程需要使用其中一个密钥，<br>解密过程需要使用另一个密钥。所以加密过程或是一个公钥操作过程或是一个私钥操作过<br>程，解密过程也一样。这两种过程都是把一个8位字符串转化成另一个8位字符串。这两个<br>过程是互相相反的，如果一个过程使用了一个实体的公钥，那么另一个过程使用同一实体的<br>私钥。加密和解密过程或是能实现典型的RSA转换，或是实现填充变换。<br><br>6、密钥生成<br>此章节描述RSA密钥生成。每个实体都需要选择一个正整数e作为它的公开指数。每<br>个实体都需要私人的随机的选择两个不同的奇素数p和q，以便e和（p-1）*（q-1）互素。<br>公开模数n是私人的素数p，q的乘积：n=p*q 。私人指数是一个正整数d，以便d*e-1可<br>以被（p-1）*（q-1）整除。模数n的字节长为k，k满足2^(8(k-1)) &lt;= n &lt; 2^(8k)。模数长度<br>k必须是至少12个字节，使之适应此文档中的块格式（见第8章）。<br>注意：<br>（1）	公开模数在特殊应用程序中可以是标准化的。在X.509的附录C中提到使用3<br>或65537可以有一些实际的好处。<br>（2）	为了使模数n的因数分解更困难，可以考虑一些额外的选择素数的条件。这些<br>保障安全的条件超出了此文档的论述范围。长度k的下限是为了适应块格式，<br>并不是为了保障安全。<br><br>7、密钥语法<br>此章节给出了RSA公钥和私钥的语法<br><br>7．1公钥语法<br>一个RSA公钥需要有ASN.1的RSAPublicKey类型：<br><br>  RSAPublicKey ::= SEQUENCE {<br>     modulus INTEGER, -- n<br>     publicExponent INTEGER -- e }<br>（这个类型被定义于X.509中，保留在此处是为了兼容性。）<br>RSAPublicKey类型的字段有下列含义：<br>modulus是模数n；<br>publicExponent是公开指数e。<br><br>7．2私钥语法<br>一个RSA私钥有一个ASN.1的RSAPrivateKey类型：<br><br>   RSAPrivateKey ::= SEQUENCE {<br>     version Version,<br>     modulus INTEGER, -- n<br>     publicExponent INTEGER, -- e<br>     privateExponent INTEGER, -- d<br>     prime1 INTEGER, -- p<br>     prime2 INTEGER, -- q<br>     exponent1 INTEGER, -- d mod (p-1)<br>     exponent2 INTEGER, -- d mod (q-1)<br>     coefficient INTEGER -- (inverse of q) mod p }<br><br>   Version ::= INTEGER<br>RSAPrivateKey类型的字段有下列含义：<br>?	version是一个为兼容将来此文档的修改的版本号。为了适应此文档的版本它<br>应该是0；<br>?	modulus是模数n；<br>?	publicExponent是公开指数e；<br>?	privateExponent是私人指数d；<br>?	prime1是组成模数n的一个素数p；<br>?	prime2是组成模数n的一个素数q；<br>?	exponent1是d mod (p-1)；<br>?	exponent2是d mod (q-1)；<br>?	coefficient是中国剩余理论中的系数q-1 mod p。<br>注意：<br>（1）	一个RSA私钥逻辑上仅包含模数n和私人指数d。p，q， d mod (p-1)， d <br>mod (p-1)和q-1 mod p的出现是为了提高效率，正如Quisquater和Couvreur<br>显示在[QC82]中。如果公钥知道的话，按照Miller[Mil76]的结果，一个不<br>包含其他值的私人密钥语法是很容易转化成此处定义的语法。<br>（2）	公开指数e的出现是为了可以容易的从私钥中得到公钥。<br><br>8、加密过程<br>此章节描述了RSA的加密过程。<br>加密过程包括4个步骤：加密块格式化，8位字符串到整数的转化，RSA计算，整数<br>到8位字符串的转化。加密过程的输入为数据8位字符串，模数n，指数c。对于公钥操作<br>来说，整数c是实体的公开指数e；对于私钥操作来说，整数c是实体的私人指数d。加密<br>过程的输出为被加密的数据，一个8位字符串ED。<br>数据D的长度不应该长于k-11个8位字节，其必为正数，因为模数的长度k是至少<br>12个8位字节。这种限制保证了填充串PS的长度至少为8个8位字节，这是一项安全措施。<br>注意：<br>（1）	在此文档的对于加密内容加密密钥和消息散列的典型应用中，||D|| &lt;= 30。这样<br>RSA模数的长度至少需要328位（41个8位字节），这是合理的，并且和安全<br>建议是一致的。<br>（2）	如果被加密的数据在传输中被破坏，加密过程并不提供一个帮助错误侦察的外<br>在的完整性检查。然而，加密块的结构保证了破坏没被检查出的可能性小于<br>2-16，这是一个随机加密块看起来像类型2的可能性的上限。<br>（3）	定义在此的对于除了包含一个消息散列的8位字节串的数据的私钥操作的应用<br>并不被推荐，需要更多的研究。<br>（4）	此文档可以被扩展，来控制长度长于k-11个8位字节串<br><br>8．1加密块格式化<br>加密块是一个8位字节串EB，由块标记BT，填充块PS和数据D组成。<br>EB = 00 || BT || PS || 00 || D          （1）<br>块标记BT是一个标记字节，表示加密块的结构。对于此文档的版本，它有00，<br>01，或02值。私钥操作为00，或01；公钥操作为02。<br>填充串PS为k-3-||D||长的8位字节字符串。对于00型，填充串为00；对于01型，<br>填充串为ff；对于02型，填充串为假散列生成的非0值。这使得加密块EB的长度为<br>k。<br>注意：<br>（1）	开始的00值字节保证了转化成整数后的加密块小于模数。<br>（2）	对于00型来说，数据D必须以一个非0字节开始，或是必须知道长度，<br>以便加密块能被清楚的解析。对于01和02型来说，加密块能被清楚的解<br>析，这是因为填充块PS不包含00值字节，它可以被一个00值字节从数据<br>D分开。<br>（3）	01型被推荐为私钥操作标志。01型有保证转化成整数的加密块很大的性<br>能，这能防止Desmedt和Odlyzko [DO86]所建议的某种攻击。<br>（4）	01和02型是和被描述在RFC1423中的PEM RSA的内容加密密钥和消息<br>散列的加密是兼容的。<br>（5）	对于02类型来说，建议为每一个加密过程都独立生成假散列字节，特别是<br>如果相同的数据被输入多于一个的加密过程。Hastad的结果 [Has88]促进<br>了这种建议。<br>（6）	对于02类型来说，填充串至少是8个字节长，这是对于公钥操作的一个安<br>全措施，为了防止攻击者通过测试所有可能的加密块来恢复数据。类似的，<br>对于01类型最小长度是一样的。<br>（7）	此文档将来可以扩展为包括其他类型。<br><br>8．2 8位字节串到整数的转换<br>加密块EB需要被转化为一个整数x，即整数加密块。从头到尾让EB1, ..., Ebk<br>组成EB字节串。然后整数x应该满足：<br>                                     k<br>                x =  SUM  2^(8(k-i)) EBi             (2)<br>                                   i = 1<br>换句话来说，EB的第一个字节在整数中意义最重大，最后一个字节的重要性最<br>低。<br>注意：因为EB1 = 00并且 2^(8(k-1)) &lt;= n，所以整数加密块x满足0 &lt;= x &lt; n。<br><br>8．3 RSA计算<br>整数加密块x需要被求c次方幂，然后模n，最后被赋给整数y，即整数被加密<br>数据。<br>y = x^c mod n,  0 &lt;= y &lt; n<br>这是一个典型的RSA计算。<br><br>8．4 整数到字节串的转换<br>整数被加密数据y需要被转换成一个长度k的8位字节串ED，即被加密数据。<br>被加密数据应该满足：<br>                                     k<br>                y =  SUM  2^(8(k-i)) EDi            (3)<br>                                   i = 1<br>这里ED1, ..., Edk就是字节串ED的组成。<br>换句话说，ED的第一个字节在整数中最为重要，ED的最后一个字节重要性最低。<br><br>9、解密过程<br>此章节描述了RSA解密过程。<br>解密过程包含4个步骤：字节串到整数的转换，RSA计算，整数到字节串的转换，和<br>需加密块解析。解密过程的输入是一个8位字节串ED，即被加密数据；模数n；指数c。对<br>一个公钥操作来说，整数c是一个实体的公开指数e；对一个私钥操作来说，整数c是一个<br>实体的私人指数d。解密过程的输出是一个8位字节串D，即原始数据。<br>如果被加密数据ED的长度不是k，则为错误。<br>简短来说，解密过程是根据加密过程来描述的。<br>9．1 字节串到整数的转换<br>被加密的数据ED根据等式（3）被转化成整数被加密数据y。<br>如果整数被加密数据不满足0 &lt;= y &lt; n，则为错误。<br><br>9．2  RSA计算<br>整数被加密数据y需要被求c次方幂，然后模n，最后被赋给整数x，即整数需加密块。<br>x = y^c mod n,  0 &lt;= x &lt; n<br>这是一个典型的RSA计算。<br><br>9．3 整数到字节串的转换<br>整数需加密块x根据等式（2）被转化成一个长度k的8位字节串EB，即需加密块。<br><br>9．4 需加密块解析<br>需加密块EB根据等式（1）被解析成一个由块标记BT，填充块PS和数据D组成的<br>数据块。<br>如果有下列情况发生，则为错误：<br>?	需加密块不能被明白的解析（见8.1节的注意）。<br>?	填充串PS少于8字节，或是和块标记BT不匹配。<br>?	解密过程是一个公钥操作过程，块标记不能为00或01；或者解密过程是一个私<br>钥操作过程，块标记不能为02。<br><br>10、签名算法<br>本章定义了3个基于被描述在第8、9章中的RSA加密过程的签名算法。签名算法主<br>要被用于签署X.509/PEM证书，CRL，PKCS #6扩展证书，以及其他使用数字签名的对象，<br>例如X.401消息环。算法并不被特意用来构建PKCS #7的数字签名。第一个签名算法把MD2<br>散列算法和RSA结合起来（简称MD2 with RSA）；第二个签名算法把MD4散列算法和RSA<br>结合起来（简称MD4 with RSA）；第三个签名算法把MD5散列算法和RSA结合起来（简<br>称MD5 with RSA）。<br>本章节描述了两个算法的签名过程和验证过程。所选的散列算法取决于签名算法，<br>MD2或MD5。签名过程使用一个实体的私钥；而验证过程使用一个实体的公钥。签名过程<br>把一个8位字节串（消息）转化成一个位串（签名）；而验证过程检验一个位串（签名）是<br>否为一个8位字节串（消息）的签名。<br>注意：被定义在此的签名算法和在PKCS #7中构建签名的方法（加密消息散列）之间<br>的仅有的不同是此处的签名用位串表示，这和X.509 SIGNED宏是一致的。在PKCS #7中<br>被加密的消息散列是8位字节串。<br><br>10．1 签名过程<br>签名过程包括4个步骤：消息散列，数据编码，RSA加密和8位字节串到位串的转换。<br>签名过程的输入是一个8位字节串M，即消息；签名者的私人密钥。其输出是一个位串S，<br>即签名。<br><br>10．1．1 消息散列<br>使用所选的消息散列算法来散列消息M，得到一个8位字节串MD，即消息散列。<br><br>10．1．2 数据编码<br>消息散列MD和消息散列算法标识符组成了以下描述的ASN.1类型DigestInfo的值，<br>此类型将通过BER编码来生成一个8位字节串D，即原始数据。<br>DigestInfo ::= SEQUENCE {<br>     digestAlgorithm DigestAlgorithmIdentifier,<br>     digest Digest }<br><br>DigestAlgorithmIdentifier ::= AlgorithmIdentifier<br><br>Digest ::= OCTET STRING<br><br>类型DigestInfo的域有下列含义：<br>?	digestAlgorithm表示用于散列的算法（以及相关参数）。对应用程序来说，它标识<br>了所选的散列算法，MD2，MD4或MD5。作为参考，以下是相关的对象标识符：<br>    md2 OBJECT IDENTIFIER ::=<br><br>     { iso(1) member-body(2) US(840) rsadsi(113549)<br>         digestAlgorithm(2) 2 } md4 OBJECT IDENTIFIER ::=<br>     { iso(1) member-body(2) US(840) rsadsi(113549)<br>         digestAlgorithm(2) 4 } md5 OBJECT IDENTIFIER ::=<br>     { iso(1) member-body(2) US(840) rsadsi(113549)<br>         digestAlgorithm(2) 5 }<br>   对这些对象标识符来说，散列算法的参数域是空。<br>?	digest是消息散列过程的结果，例如消息散列MD。<br><br>注意：<br>1.	DigestInfo值包含了一个消息散列算法标识符，用来限制由于使用消息散列算法<br>压缩数据而导致的破坏。举例来说，如果攻击者能够找出带有给定的MD2消息<br>散列的消息，那么他就可以通过找出一个表面无害的带有相同MD2散列的消息，<br>并强迫签名者签署这个表面无害的消息，来伪造消息签名。这种攻击方法只有在<br>使用MD2散列算法时才会成功。如果DigestInfo值只包括消息散列，攻击者就能<br>攻击使用任何消息散列的签名者。<br>2.	虽然使用SEQUENCE类型违背了在X.509 SIGNED和SIGNATURE宏中的签名<br>是一个ENCRYPTED OCTET STRING的书面声明，但是正如I'Anson和Mitchell<br>在[IM90]中指出的，这样的书面阐明并不被要求。<br>3.	没有理由说MD4不是一个安全度很高的数字签名方案，但是由于MD4被设计的<br>非常快，所以它处于被成功攻击的危险中。如果有人找出拥有同一个散列的两个<br>消息这样的冲突，那么这个散列算法可以被认为是打破的（broken）。当冲突被发<br>现在仅有两个散列循环[Mer90][dBB92]的MD4的变体中，并没有冲突出现在有三<br>个散列循环的MD4中。在进一步的研究后，我们可以认为MD4有很高的安全性。<br>MD5有四个散列循环，比MD4更慢。在MD4被研究前，它是被推荐使用的。<br>在MD5内部的压缩功能[dBB93]中的假冲突并没有任何实际的安全影响。<br>MD2是三者中最慢的一个，它有最保守的设计，没有任何对MD2的攻击被公布<br>出来。<br><br>10．1．3  RSA加密<br>正如在第7章中描述的数据D被签名者的RSA私钥加密，生成一个8位字节串ED，<br>即被加密的数据。其块标记为01（见8.1节）。<br><br>10．1．4  8位字节串到位串的转换<br>被加密数据ED被转换成一个位串S，即签名。具体来说，被加密数据的第一个字节<br>的第一位成为签名的第一个数据位，以此类推，直到被加密数据的最后一个字节的最后一位，<br>它将变成签名的最后一个数据位。<br>注意：签名S的位长度是8的倍数。<br><br>10．2 验证过程<br>验证过程包括四个步骤：位串到字节串的转换，RSA解密，数据解码，消息散列和比<br>较。验证过程的输入是字节串M，即消息；签名者的公钥；位串S，即签名。其输出是验证<br>成功或失败的标记号。<br><br>10．2．1 位串到字节串的转换<br>签名S被转换成字节串ED，即被加密的数据。具体来说，假设S的位长度是8的倍<br>数，S的第一位将变成字节串的第一个字节的第一位，以此类推，直到签名的最后一位变成<br>字节串的最后一个字节的最后一位。<br>如果签名的位长度不是8的倍数，则是错误。<br><br>10．2．2 RSA解密<br>正如在第8章节中描述的使用签名者的公钥对被加密数据ED进行解密，得到字节串<br>D，即原始数据。<br>如果在解密过程中恢复的块标记位不是01，则是错误的（见9.4节）。<br><br>10．2．3 数据解码<br>原始数据D将被BER解码为类型DigestInfo的ASN.1值，此值被分成消息散列MD<br>和消息散列算法标识符。消息散列算法标识符决定了下一步所选的消息散列算法。<br>如果消息散列算法标识符不是MD2，MD4或MD5消息散列算法，则为错误。<br><br>10．2．4 消息散列和比较<br>使用所选的消息散列算法对消息M进行散列，得到字节串MD`，即将进行比较的消<br>息散列。如果MD`和MD相同，则表示验证成功，否则为失败。<br><br>11、对象标识符<br>本文档定义了5个对象标识符：pkcs-1，rsaEncryption，md2WithRSAEncryption，<br>md4WithRSAEncryption和md5WithRSAEncryption。<br>对象标识符pkcs-1等同于本篇文档。<br>pkcs-1 OBJECT IDENTIFIER ::=<br><br>     { iso(1) member-body(2) US(840) rsadsi(113549)<br>         pkcs(1) 1 }<br>对象标识符rsaEncryption等同于定义在第7章节中的RSA公/私钥和定义在第8、9章<br>节中的RSA加/解密过程。<br>rsaEncryption OBJECT IDENTIFIER ::= { pkcs-1 1 }<br>rsaEncryption对象标识符被用于AlgorithmIdentifier类型的algorithm域的一个值。此<br>类型的parameters域有算法特定的语法ANY DEFINED BY algorithm，在rsaEncryption算法<br>中，其值为空。<br>对象标识符md2WithRSAEncryption，md4WithRSAEncryption和<br>md5WithRSAEncryption各自表示定义在第10章节中的MD2 with RSA，MD4 with RSA和<br>MD5 with RSA签名及验证过程。<br>   md2WithRSAEncryption OBJECT IDENTIFIER ::= { pkcs-1 2 }<br>   md4WithRSAEncryption OBJECT IDENTIFIER ::= { pkcs-1 3 }<br>   md5WithRSAEncryption OBJECT IDENTIFIER ::= { pkcs-1 4 }<br>这些对象标识符被用于AlgorithmIdentifier类型中的algorithm域的一个值。此类型的<br>parameters域有算法特定的语法ANY DEFINED BY algorithm，在此三个算法中，其值为空。<br>注意：X.509的对象标识符rsa也表示定义在第7章节中的RSA公钥，但并不表示私钥，<br>并且表示不同的加/解密过程。一些应用程序期望将鉴别RSA公钥。这些公钥和本文档是兼<br>容的，使用RSA公钥的rsaEncryption过程等同于使用rsaEncryption公钥的rsaEncryption过<br>程。<br><br><br>安全考虑<br>安全内容在此备忘录中讨论。<br><br>修订版记录<br>版本1.0-1.3<br>此版本在1991的2月和3月被分发给RSA Data Security, Inc.的 Public-Key <br>Cryptography Standards会议的参加者。<br><br>版本1.4<br>此版本是在1991.6.3的第一次公开发布的PKCS中的一部分内容，并被发行作为<br>NIST/OSI Implementors的工作组文档SEC-SIG-91-18。<br><br>版本1.5<br>此版本包括了几处改变，其中有参考的更新和修订版记录的增加。下列是几处实质的<br>改变：<br>?	第10章节：增加了MD4 with RSA的签名和验证过程。<br>?	第11章节：增加了md4WithRSAEncryption对象标识符。<br>代替1991.6.3的版本，它也被作为NIST/OSI Implementors的工作组文档<br>SEC-SIG-91-18。<br><br>鸣谢<br>本文档基于RSA Data Security, Inc.的一个部门RSA Laboratories的撰稿。任何实质的<br>使用本文档都必须感谢RSA Data Security, Inc.。RSA Data Security, Inc.要求所有对此文档的<br>资料的阐述和参考都必须表示为RSA Data Security, Inc. PKCS #1。<br><br>作者地址<br><br>   Burt Kaliski<br>   RSA Laboratories East<br>   20 Crosby Drive<br>   Bedford, MA  01730<br><br>   Phone: (617) 687-7000<br>   EMail: burt@rsa.com<br><br>版权声明<br>Copyright (C) The Internet Society (1998).  All Rights Reserved.<br><br>   This document and translations of it may be copied and furnished to others, and derivative <br>works that comment on or otherwise explain it or assist in its implementation may be prepared, <br>copied, published and distributed, in whole or in part, without restriction of any kind, provided <br>that the above copyright notice and this paragraph are included on all such copies and derivative <br>works. However, this document itself may not be modified in any way, such as by removing the <br>copyright notice or references to the Internet Society or other Internet organizations, except as <br>needed for the purpose of developing Internet standards in which case the procedures for <br>copyrights defined in the Internet Standards process must be followed, or as required to translate it <br>into languages other than English.<br>   The limited permissions granted above are perpetual and will not be revoked by the Internet <br>Society or its successors or assigns.<br>   This document and the information contained herein is provided on an "AS IS" basis and THE <br>INTERNET SOCIETY AND THE INTERNET ENGINEERING TASK FORCE DISCLAIMS <br>ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY <br>WARRANTY THAT THE USE OF THE INFORMATION HEREIN WILL NOT INFRINGE <br>ANY RIGHTS OR ANY IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS <br>FOR A  PARTICULAR PURPOSE.<br><br>RFC2313——PKCS #1: RSA EncryptionVersion 1.5                      PKCS#1：RSA加密 版本1.5<br><br><br>1<br>RFC文档中文翻译计划<br><br><br></pre><img src ="http://www.cppblog.com/Khan/aggbug/24282.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-05-17 13:54 <a href="http://www.cppblog.com/Khan/archive/2007/05/17/24282.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>perl的常用基本语法例子</title><link>http://www.cppblog.com/Khan/archive/2007/04/20/22367.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Fri, 20 Apr 2007 05:27:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/04/20/22367.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/22367.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/04/20/22367.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/22367.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/22367.html</trackback:ping><description><![CDATA[<div style="border: 1px solid #cccccc; padding: 4px 5px 4px 4px; background-color: #eeeeee; font-size: 13px; width: 98%;"><!--<br><br>Code highlighting produced by Actipro CodeHighlighter (freeware)<br>http://www.CodeHighlighter.com/<br><br>--><span style="color: #008000;">#</span><span style="color: #008000;">!/usr/bin/perl&nbsp;-w</span><span style="color: #008000;"><br></span><span style="color: #000000;"><br></span><span style="color: #0000ff;">use</span><span style="color: #000000;">&nbsp;strict;&nbsp;</span><span style="color: #008000;">#</span><span style="color: #008000;">使用严格语法</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">use</span><span style="color: #000000;">&nbsp;DBI;<br><br><br></span><span style="color: #0000ff;">sub</span><span style="color: #000000;">&nbsp;set_GBK4Mysql{<br>&nbsp;&nbsp;</span><span style="color: #008000;">#</span><span style="color: #008000;">设定数据库字符集</span><span style="color: #008000;"><br></span><span style="color: #000000;">&nbsp;&nbsp;</span><span style="color: #0000ff;">my</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$sql</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000; font-weight: bold;">SET&nbsp;CHARACTER&nbsp;SET&nbsp;GBK</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000;">;<br>&nbsp;&nbsp;</span><span style="color: #0000ff;">my</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$sth</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$_</span><span style="color: #000000;">&nbsp;[</span><span style="color: #800000;">0</span><span style="color: #000000;">]</span><span style="color: #000000;">-&gt;</span><span style="color: #0000ff;">do</span><span style="color: #000000;">(</span><span style="color: #800080;">$sql</span><span style="color: #000000;">);<br>}<br><br><br><br><br><br><br></span><span style="color: #008000;">#</span><span style="color: #008000;">检查mysql驱动是否安装</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">my</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$drh</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;DBI</span><span style="color: #000000;">-&gt;</span><span style="color: #000000;">install_driver(&nbsp;</span><span style="color: #000000; font-weight: bold;">'</span><span style="color: #000000; font-weight: bold;">mysql</span><span style="color: #000000; font-weight: bold;">'</span><span style="color: #000000;">&nbsp;);<br></span><span style="color: #0000ff;">if</span><span style="color: #000000;">&nbsp;(&nbsp;</span><span style="color: #000000;">!</span><span style="color: #0000ff;">defined</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$drh</span><span style="color: #000000;">&nbsp;)&nbsp;{<br>&nbsp;&nbsp;</span><span style="color: #0000ff;">die</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000; font-weight: bold;">不能装入mysql驱动:&nbsp;$!\n</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000;">;<br>}<br><br><br><br></span><span style="color: #008000;">#</span><span style="color: #008000;">连接mysql数据库</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">my</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$dbh</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;DBI</span><span style="color: #000000;">-&gt;</span><span style="color: #0000ff;">connect</span><span style="color: #000000;">(</span><span style="color: #000000; font-weight: bold;">'</span><span style="color: #000000; font-weight: bold;">DBI:mysql:dbname=cm3gw;host=127.0.0.1;port=13306</span><span style="color: #000000; font-weight: bold;">'</span><span style="color: #000000;">,</span><span style="color: #000000;"><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #000000; font-weight: bold;">'</span><span style="color: #000000; font-weight: bold;">sioa_m3</span><span style="color: #000000; font-weight: bold;">'</span><span style="color: #000000;">,</span><span style="color: #000000; font-weight: bold;">'</span><span style="color: #000000; font-weight: bold;">sioa_m3</span><span style="color: #000000; font-weight: bold;">'</span><span style="color: #000000;">)&nbsp;or&nbsp;</span><span style="color: #0000ff;">die</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$DBI</span><span style="color: #000000;">::</span><span style="color: #000000;">errstr;<br><br></span><span style="color: #000000;">&amp;</span><span style="color: #000000;">set_GBK4Mysql(</span><span style="color: #800080;">$dbh</span><span style="color: #000000;">);<br><br><br></span><span style="color: #0000ff;">my</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$query</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000; font-weight: bold;">Select&nbsp;sp_port,service_name,&nbsp;memo&nbsp;</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000;"><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #000000;">.</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000; font-weight: bold;">&nbsp;From&nbsp;sp_service_list</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000;"><br>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #000000;">.</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000; font-weight: bold;">&nbsp;Where&nbsp;flag&nbsp;=&nbsp;1&nbsp;</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000;">;<br><br><br><br><br></span><span style="color: #008000;">#</span><span style="color: #008000;">执行有结果集sql</span><span style="color: #008000;"><br></span><span style="color: #0000ff;">my</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$sth</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$dbh</span><span style="color: #000000;">-&gt;</span><span style="color: #000000;">prepare(</span><span style="color: #800080;">$query</span><span style="color: #000000;">)&nbsp;or&nbsp;</span><span style="color: #0000ff;">die</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000; font-weight: bold;">Can't&nbsp;prepare&nbsp;$query:&nbsp;$dbh-&gt;errstr\n</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000;">;<br><br></span><span style="color: #0000ff;">my</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$result</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$sth</span><span style="color: #000000;">-&gt;</span><span style="color: #000000;">execute&nbsp;or&nbsp;</span><span style="color: #0000ff;">die</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000; font-weight: bold;">can't&nbsp;execute&nbsp;the&nbsp;query:&nbsp;$sth-&gt;errstr</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000;">;&nbsp;<br><br></span><span style="color: #0000ff;">while</span><span style="color: #000000;">(</span><span style="color: #0000ff;">my</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">@row</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000;">=</span><span style="color: #000000;">&nbsp;</span><span style="color: #800080;">$sth</span><span style="color: #000000;">-&gt;</span><span style="color: #000000;">fetchrow_array)&nbsp;{&nbsp;<br>&nbsp;&nbsp;</span><span style="color: #0000ff;">print</span><span style="color: #000000;">&nbsp;</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000; font-weight: bold;">$row[0]\t$row[1]\t$row[2]\n</span><span style="color: #000000; font-weight: bold;">"</span><span style="color: #000000;">;&nbsp;<br>}<br><br>&nbsp;<br><br></span><span style="color: #008000;">#</span><span style="color: #008000;">&nbsp;指示没有更多的数据可以被取出,释放语句句柄,并且释放系统资源</span><span style="color: #008000;"><br></span><span style="color: #800080;">$sth</span><span style="color: #000000;">-&gt;</span><span style="color: #000000;">finish;&nbsp;<br><br></span><span style="color: #008000;">#</span><span style="color: #008000;">关闭连接</span><span style="color: #008000;"><br></span><span style="color: #800080;">$dbh</span><span style="color: #000000;">-&gt;</span><span style="color: #000000;">disconnect;<br></span></div>
<br><img src ="http://www.cppblog.com/Khan/aggbug/22367.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-04-20 13:27 <a href="http://www.cppblog.com/Khan/archive/2007/04/20/22367.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>makefile的常用方法</title><link>http://www.cppblog.com/Khan/archive/2007/03/28/20762.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Wed, 28 Mar 2007 06:26:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/03/28/20762.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/20762.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/03/28/20762.html#Feedback</comments><slash:comments>2</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/20762.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/20762.html</trackback:ping><description><![CDATA[# Project: m3server<br /># Makefile created by Khan.Lau<br /><br /># 应用程序名<br />BIN  = m3server.exe<br />LIB  = m3server.a<br /><br /># 输出目录<br />CONFIGURATION  = debug<br />#CONFIGURATION = release<br /><br /># 取得项目的当前工作路径<br />PROJECT_PATH := $(shell cd)\src<br /><br />CPP  = g++<br />CC   = gcc<br /><br />COMPILER = $(CPP)<br /><br /><br /># c/c++库路径<br />LIBPATH = "D:/Develop/CPlus/MinGW/lib"<br />    <br /><br />WINDRES = windres.exe<br />RES  = <br /><br />LINKOBJ  = $(CONFIGURATION)/Khan_Queue.o \<br />    $(CONFIGURATION)/db_mysql.o \<br />    $(CONFIGURATION)/ThreadPool.o \<br />    $(CONFIGURATION)/Util.o \<br />    $(CONFIGURATION)/m3server.o \<br />    $(CONFIGURATION)/CppObject.o \<br />    $(CONFIGURATION)/CppSocket.o \<br />    $(CONFIGURATION)/CppUdpSocket.o \<br />    $(CONFIGURATION)/CppServerSocket.o \<br />    $(CONFIGURATION)/ReadConfig.o \<br />    $(RES)<br /><br /># 包路径<br />LIBS =  -L$(LIBPATH)\<br />    -lws2_32\<br />    -L"D:/Develop/CPlus/mysql5.0/lib" -lmysql\<br />    -L"D:/Develop/CPlus/pthread/Pre-built.2/lib" -lpthreadGC2<br /><br /><br /><br /># c的类库路径<br />INCS =  -I$(LIBPATH)/include<br /><br /><br /># c++的类库路径<br />CXXINCS =  -I$(LIBPATH)/include\<br />    -I$(LIBPATH)/include/c++/3.2.3\<br />    -I$(LIBPATH)/include/c++/3.2.3/backward\<br />        -I$(LIBPATH)/include/c++/3.2.3/mingw32\<br />    -I"D:/Develop/CPlus/pthread/Pre-built.2/include"\<br />    -I$(PROJECT_PATH)\<br />    -I"D:/Develop/CPlus/mysql5.0/include"<br /><br />CXXFLAGS = -g -Wall $(CXXINCS)  <br />CFLAGS = -g -Wall $(INCS)  <br />RM = rm -f<br /><br />.PHONY: all all-before all-after clean clean-custom rebuild strip<br /><br />all: all-before $(LIB) $(BIN) all-after<br /><br />clean: clean-custom<br />    ${RM} $(LINKOBJ) $(CONFIGURATION)/$(BIN) $(CONFIGURATION)/$(LIB)<br /><br /><br />#打包静态库<br />$(LIB): $(LINKOBJ)<br />    ar -r $(CONFIGURATION)/$(LIB) $(LINKOBJ) <br /><br />$(BIN): $(LINKOBJ)<br />    $(COMPILER) $(CONFIGURATION)/$(LIB)  -o $(CONFIGURATION)/$(BIN) $(LIBS)<br /><br /><br />#缩减可执行文件大小<br />strip: <br />    strip $(CONFIGURATION)/$(BIN)<br /><br />##################################################################################<br /><br />#类库<br />$(CONFIGURATION)/Khan_Queue.o: src/lib/Khan_Queue.c<br />    $(COMPILER) -c src/lib/Khan_Queue.c -o $(CONFIGURATION)/Khan_Queue.o $(CXXFLAGS)<br /><br />$(CONFIGURATION)/db_mysql.o: src/lib/db_mysql.c<br />    $(COMPILER) -c src/lib/db_mysql.c -o $(CONFIGURATION)/db_mysql.o $(CXXFLAGS)<br /><br />$(CONFIGURATION)/ThreadPool.o: src/lib/ThreadPool.c<br />    $(COMPILER) -c src/lib/ThreadPool.c -o $(CONFIGURATION)/ThreadPool.o $(CXXFLAGS)<br /><br />$(CONFIGURATION)/Util.o: src/lib/Util.c<br />    $(COMPILER) -c src/lib/Util.c -o $(CONFIGURATION)/Util.o $(CXXFLAGS)<br /><br />$(CONFIGURATION)/CppObject.o: src/lib/CppObject.cpp<br />    $(COMPILER) -c src/lib/CppObject.cpp -o $(CONFIGURATION)/CppObject.o $(CXXFLAGS)<br /><br />$(CONFIGURATION)/CppSocket.o: src/lib/CppSocket.cpp<br />    $(COMPILER) -c src/lib/CppSocket.cpp -o $(CONFIGURATION)/CppSocket.o $(CXXFLAGS)<br /><br />$(CONFIGURATION)/CppUdpSocket.o: src/lib/CppUdpSocket.cpp<br />    $(COMPILER) -c src/lib/CppUdpSocket.cpp -o $(CONFIGURATION)/CppUdpSocket.o $(CXXFLAGS)<br /><br />$(CONFIGURATION)/CppServerSocket.o: src/lib/CppServerSocket.cpp<br />    $(COMPILER) -c src/lib/CppServerSocket.cpp -o $(CONFIGURATION)/CppServerSocket.o $(CXXFLAGS)<br /><br />$(CONFIGURATION)/ReadConfig.o: src/lib/ReadConfig.cpp<br />    $(COMPILER) -c src/lib/ReadConfig.cpp -o $(CONFIGURATION)/ReadConfig.o $(CXXFLAGS)<br /><br />###################################################################################<br /><br />#核心代码<br />$(CONFIGURATION)/m3server.o: src/kernel/m3server.cpp<br />    $(COMPILER) -c src/kernel/m3server.cpp -o $(CONFIGURATION)/m3server.o $(CXXFLAGS)<br /><br />###################################################################################<br /><br />rebuild: clean all<br /><br /><br /><br /><img src ="http://www.cppblog.com/Khan/aggbug/20762.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-03-28 14:26 <a href="http://www.cppblog.com/Khan/archive/2007/03/28/20762.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>关于Pthreadpool的讨论</title><link>http://www.cppblog.com/Khan/archive/2007/03/19/20134.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Mon, 19 Mar 2007 05:04:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/03/19/20134.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/20134.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/03/19/20134.html#Feedback</comments><slash:comments>2</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/20134.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/20134.html</trackback:ping><description><![CDATA[羞答答的小二(42524783) 10:55:53<br />
发放线程我的理解是..做一个函数指针..当参数传递到线程内部..执行.<br /><br />cyt 10:57:01<br />函数指针放进队列，线程捡到指针就干活；干完继续等待队列 <br /><br />忧郁的老鸨 10:57:02<br />还是那句话，搞清楚使用pool的原因 <br /><br />羞答答的小二 10:57:52<br />回收是不是就是传递进去的那个任务函数执行完了..让他wait在那里 <br /><br />羞答答的小二 10:58:23<br />我有觉悟..所以我要使用pool..不清楚的只是一些细节部分 <br /><br />cyt 10:58:23<br />yes，回收就是重新回到等待任务队列的状态 <br /><br /><br />
羞答答的小二 10:58:41<br />
明白了..拜谢p大 <br /><br />清澈的progame 10:59:50<br />线程那里不是一上来就是消费者生产者那个例子么 <br /><br />cyt 11:00:13<br />对，其实就是生产者消费者模型 <br /><br />白粉4号 11:01:13<br />消费完了，有唤醒功能多好 <br /><br />cyt 11:01:49<br />没有唤醒的吗？ <br /><br />羞答答的小二 11:01:50<br />//ThreadPool.h<br /><br />#ifndef THREADPOOL_H_<br />#define THREADPOOL_H_<br /><br /><br />#ifdef __cplusplus<br />extern "C" {  <br />#endif<br /><br /><br /><br />#define MAX_THREAD_POOL 200 <br /><br /><br />typedef void* threadpool;<br />typedef void* (*dispatch_fn)(void *);<br /><br />threadpool create_threadpool(int p_iThreadsPool);<br />int dispatch_threadpool(threadpool from_me, dispatch_fn dispatch_to_here, void* arg);<br />void distory_threadpool(threadpool distoryme);<br /><br />#ifdef __cplusplus<br />}<br />#endif<br /><br />#endif //THREADPOOL_H_ <br /><br /><br />清澈的progame 11:01:50<br />要么你自己轮询 要么唤醒也可以 委托或事件 <br /><br />羞答答的小二 11:02:06<br />...没有唤醒就轮<br />有唤醒就唤醒 <br /><br />羞答答的小二 11:02:29<br />cond 和 mulex <br /><br />羞答答的小二 11:02:52<br />轮是一种卑劣的行为... <br /><br />cyt 11:03:12<br />嗯，是一种严重罪行 <br /><br />羞答答的小二 11:03:33<br />为高风亮节d偶所不齿...所以..bb..偶bs你 <br /><br />忧郁的老鸨 10:57:02<br /> 自己实现pool....... 貌似你还明白原理。。。。只是在强行使用而已 <br /><br />羞答答的小二 11:04:38<br /> 是试试使用下..看看效果.. <br />  <br />羞答答的小二 11:05:21<br />找了篇代码改了改..然后找你们印证下我的理解有没有错 <br /><br />忧郁的老鸨 11:06:27<br />你在理解怎么用，但貌似没有去想为什么用 <br /><br />羞答答的小二 11:07:15<br />节省大量 create和distory的时间 <br /><br />忧郁的老鸨 11:07:39<br />何解？ <br /><br />羞答答的小二 11:07:57<br />因为一早create好了... <br /><br />忧郁的老鸨 11:08:40<br />你指什么的create和destroy <br /><br />羞答答的小二 11:09:43<br />比如偶去欢场... 一下来来了一堆粉头..偶爱要哪个要哪个..比来一个看一个效率高得多..大家都挑完了..众粉头就鸟兽散了 <br /><br />cyt 11:09:48<br />减少thread的创建和销毁时间 <br /><br />清澈的progame 11:10:23<br />不是这样的 是粉头要干活化妆什么的太费时间了 <br /><br />清澈的progame 11:10:36<br />干脆接完客就不要卸了 <br /><br />羞答答的小二 11:11:05<br />..... <br /><br />羞答答的小二 11:11:19<br />  清洗下都是要d... <br /><br />cyt 11:11:22<br />嗯，直接躺在那里等progame <br /><br />忧郁的老鸨 11:11:30<br />都对，thread开销和超大对象的创建都需要时间，都可以用pool，但是两种处理方式是不同的 <br /><br />羞答答的小二 11:11:44<br />用完了..就放回大堂  <br /><br />羞答答的小二 11:11:57<br />等下一拨人... <br /><br />清澈的progame 11:12:21<br />关键在于不要卸妆 如果化妆时间快 就无所谓了 <br /><br />清澈的progame 11:12:29<br />还有一点就是有时候客人太多 <br /><br />清澈的progame 11:12:34<br />小姐不够 <br /><br />清澈的progame 11:12:41<br />那就必须队列了 <br /><br />忧郁的老鸨 11:12:48<br />但是把小姐收拢起来也是一个很耗时间的动作。。。。 <br /><br />羞答答的小二 11:13:08<br />小姐随身带了bp机 <br /><br />清澈的progame 11:13:09<br />否则客人就会跑掉了 这叫并发太大  <br /><br />忧郁的老鸨 11:13:09<br />所以这是2种使用pool的理由。。。。。 <br /><br />忧郁的老鸨 11:13:52<br />用bp机call那就不是pool了 <br /><br />忧郁的老鸨 11:14:07<br />先抓过来扔在大厅里才是pool <br /><br />羞答答的小二 11:14:08<br />完事后看到bp上有消息..即刻回到大堂 <br /><br />清澈的progame 11:14:22<br />应该是小姐主动 <br /><br />羞答答的小二 11:14:30<br />如果没有完事...崔一崔客人 <br /><br />清澈的progame 11:14:34<br />完事后主动看大堂有没有客 <br /><br />清澈的progame 11:14:56<br />有的话就接过来 当然还得锁一下 否则会两个小姐拉到同一个客人 <br /><br />忧郁的老鸨 11:15:16<br /> 催客人。。。。。你这属于反人性，没几次客人就不来了 <br /><br />羞答答的小二 11:15:52<br />那也不能任由嫖客躺身上睡觉啊 <br /><br />忧郁的老鸨 11:15:55<br />客人正在爽的时候，你催一下，结果被吓痿了，责任算谁的 <br /><br />羞答答的小二 11:16:19<br />所以...适当的时候催一催是必要d  <br /><br />忧郁的老鸨 11:16:22<br />找小姐的目的就是爽，不是赶时间。。。。。  <br /><br />忧郁的老鸨 11:16:57<br />即便催，也是提醒性质，不可能强行催促 <br /><br />cyt 11:16:58<br />不是，是老鸨站在门口，有mm ready，老鸨就举起个牌子 <br /><br />忧郁的老鸨 11:17:27<br />我就是pool的管理者，俗称楼面经理。。。。。。 <br /><br /><br />羞答答的小二 11:17:57<br /> 到最后...是老鸨随便推一个出去..完全不理会嫖客看不看得上眼了 <br /><br />白粉4号 11:18:03<br />老鸨让她们换服装 <br /><br />忧郁的老鸨 11:18:29<br />嫖客自己会去挑。。。。。偶只负责开房间。。。。。 <br /><br />羞答答的小二 11:19:23<br />  你是老鸨..不是龟奴..开房间领进门是你手下的工作 <br /><br />忧郁的老鸨 11:19:35<br />有时候小姐有病了，我还需要让她们去看病。。。。。。 <br /><br />清澈的progame 11:20:02<br />我是医生 <br /><br />忧郁的老鸨 11:20:05<br />但是总有小姐不报告嫖客不知道，结果嫖客就中标了，于是产生异常。。。。。 <br /><br />清澈的progame 11:20:07<br />看病找我 <br /><br />忧郁的老鸨 11:20:27<br />表伪装编译器。。。。。 <br /><br />清澈的progame 11:21:37<br />我是虚拟机 <br /><br />清澈的progame 11:21:44<br />你们都归我管 <br /><br />白粉4号 11:22:15<br />妈的,停电 <br /><br /><img src ="http://www.cppblog.com/Khan/aggbug/20134.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-03-19 13:04 <a href="http://www.cppblog.com/Khan/archive/2007/03/19/20134.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Linux内核引导分析</title><link>http://www.cppblog.com/Khan/archive/2007/03/02/19105.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Fri, 02 Mar 2007 01:44:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2007/03/02/19105.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/19105.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2007/03/02/19105.html#Feedback</comments><slash:comments>1</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/19105.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/19105.html</trackback:ping><description><![CDATA[
		<div align="left">
				<p>MOVW 指令<br /></p>
				<p>MOVW：将DS:SI的内容送至ES:DI，是复制过去，原来的代码还在。很多书用了“移”这个字，实际上是复制过去。每次复制.DS:SI ,ES:DI自动加1<br /></p>
				<p>Linux内核中引导部分一开始有这样一段代码：</p>
				<p>45 entry start ! 告知连接程序，程序从start 标号开始执行。<br />46 start:<br />47 mov ax,#BOOTSEG ! 将ds 段寄存器置为0x7C0；<br />48 mov ds,ax<br />49 mov ax,#INITSEG    ! 将es 段寄存器置为0x9000；<br />50 mov es,ax<br />51 mov cx,#256             ! 移动计数值=256 字；<br />52 sub si,si                    ! 源地址 ds:si = 0x07C0:0x0000<br />53 sub di,di                    ! 目的地址 es:di = 0x9000:0x0000<br />54 rep                              ! 重复执行，直到cx = 0<br />55 movw                          ! 移动1 个字；<br />56 jmpi go,INITSEG      ! 间接跳转。这里INITSEG 指出跳转到的段地址。<br />57 go: mov ax,cs            ! 将ds、es 和ss 都置成移动后代码所在的段处(0x9000)。<br /><br />! 47--56 行作用是将自身(bootsect)从目前段位置0x07c0(31k)<br />! 移动到0x9000(576k)处，共256 字（512 字节），然后跳转到<br />! 移动后代码的go 标号处，也即本程序的下一语句处。</p>
				<p>注意，在55行执行完毕之后，0x7c00之后的512字节应当与0x9000之后的512字节一模一样。<br />然后看56行，这里的go是段内偏移，也就是0x39(十进制的57)，而INITSEG=0x9000，所以执行这条语句是跳到0x9000:0x39也就是复制过去的第57行，这样代码就相当于在一个程序里继续执行了。</p>----------------------------------------------------<br />REP指令<br /><br />每次执行rep指令，CX减1，然后判断CX是否等于0，如果不为0则继续执行rep指令后的串操作指令，直到CX为0，实现重复。<br /><p>----------------------------------------------------<br /></p><p>Jmpi指令</p><p>段间跳转，其Opcode为Eah，其格式为：jmpi Offset, 
          Segment Selector</p><p><br /></p></div>
<img src ="http://www.cppblog.com/Khan/aggbug/19105.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2007-03-02 09:44 <a href="http://www.cppblog.com/Khan/archive/2007/03/02/19105.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>如何kill掉进程名包含某个字符串的一批进程, 以及观测进程名包含某个字符串的进程详细信息</title><link>http://www.cppblog.com/Khan/archive/2006/12/08/16139.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Fri, 08 Dec 2006 09:44:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2006/12/08/16139.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/16139.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2006/12/08/16139.html#Feedback</comments><slash:comments>3</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/16139.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/16139.html</trackback:ping><description><![CDATA[ 今天写了两个比较得意的命令, 来炫耀一下, 嘿嘿<br /><br />如何kill掉进程名包含某个字符串的一批进程:<br />#!/bin/sh<br />kill -9 $(ps -ef|grep 进程名关键字|gawk '$0 !~/grep/ {print $2}' |tr -s '\n' ' ')<br /><br /><br /><br />观测进程名包含某个字符串的进程详细信息:<br />#!/bin/sh<br />top -c -p $(ps -ef|grep 进程名关键字|gawk '$0 !~/grep/ {print $2}' |tr -s '\n' ','|sed 's/,$/\n/')<br /><img src ="http://www.cppblog.com/Khan/aggbug/16139.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2006-12-08 17:44 <a href="http://www.cppblog.com/Khan/archive/2006/12/08/16139.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>一个小型的无线路由器 Linux 系统OpenWRT</title><link>http://www.cppblog.com/Khan/archive/2006/11/23/15573.html</link><dc:creator>Khan</dc:creator><author>Khan</author><pubDate>Thu, 23 Nov 2006 02:02:00 GMT</pubDate><guid>http://www.cppblog.com/Khan/archive/2006/11/23/15573.html</guid><wfw:comment>http://www.cppblog.com/Khan/comments/15573.html</wfw:comment><comments>http://www.cppblog.com/Khan/archive/2006/11/23/15573.html#Feedback</comments><slash:comments>7</slash:comments><wfw:commentRss>http://www.cppblog.com/Khan/comments/commentRss/15573.html</wfw:commentRss><trackback:ping>http://www.cppblog.com/Khan/services/trackbacks/15573.html</trackback:ping><description><![CDATA[作者: Cody Teng<br />
网址: <a href="http://www.eosp.org/" target="_blank">http://www.eosp.org</a><br />
郵箱: <a href="mailto:cody@eosp.org">cody@eosp.org</a><br /><br /><br /> OpenWRT - (<a href="http://www.openwrt.org/" target="_blank">http://www.openwrt.org</a>)<br /><br />
开发板: 十几种市面上很容易买到的无线路由器,价钱500元左右, 请看硬件列表: (<a href="http://wiki.openwrt.org/TableOfHardware" target="_blank">http://wiki.openwrt.org/TableOfHardware</a>)<br /><br />
我使用的是 Linksys WRT54G:<br />
CPU: MIPS 200MHZ<br />
内存: 16M<br />
ROM: 4M<br />
网络接口: 4个LAN, 1个WAN, 1个Wireless Lan<br />
已加接SD Card, 双串口和JTAG<br />
详细请看这里: (<a href="http://www.eosp.org/?page_id=20" target="_blank">http://www.eosp.org/?page_id=20</a>)<br /><br />
在开发前可先安装使用jffs2(可读写)文件系统的Firmware, 了解系统架构, 安装软件, 内建HTTP, DHCP, DNS, SSH, Telnet, PPPOE, PPTP等, 有WEB界面,<br />
另外可加装软件有7百多个选择, 包括Samba, mysql, OpenVPN, Asterisk,<br /><br />
软件列表:<br /><a href="http://tracker.openwrt.org/packages/" target="_blank">http://tracker.openwrt.org/packages/</a><br /><br />
到熟悉后使用Buildroot 做交叉编译等工作, 自后打包软件, 制作自己的Firmware, 进入嵌入式Linux 的世界.<br /><br />
学习后还可以继续充当家里无线路由器的角色, 或你改装后的小型Linux服务器!!!<br /><br /><br /><strong>这是安装 OpenWRT 的步驟<br /><br /></strong>
注: 转贴时请保持文章的完整性.<br /><br />
在安装 OpenWrt 之前，首先你要知道你所使用的无线路由器 OpenWrt 是否支持，在 OpenWrt 的网页上提供了一个路由器列表，地址是： <br /><a href="http://wiki.openwrt.org/TableOfHardware" target="_blank">http://wiki.openwrt.org/TableOfHardware</a> 。<br /><br />
当中最多人使用的是 Linksys WRT54G/GS 和 ASUS
WL-500G，相关的文档也较多，Linksys在前面已经介绍过，我在这里不再重复了，其次是 ASUS WL-500G，
原因是它在市面容易找到，而且支持
USB，即使价钱比一般的无线路由器贵1百多元，也相当值得，有了USB，你可以接上一个掫像头，移动盘，硬盘和打印机等设备。接下来我会说明
OpenWrt 在 WRT54G上的安装过程。<br /><br />
首先，到 OpenWrt 下载 Firmware，地址是：<br /><br /><a href="http://downloads.openwrt.org/whiterussian/rc4/bin/" target="_blank">http://downloads.openwrt.org/whiterussian/rc4/bin/</a><br /><br />
OpenWrt 提供很多版本的 Firmware下载，例如
openwrt-brcm-2.4-jffs2-4MB.trx，其中brcm是通用版本，如果你ASUS的路由器就属于这类；2.4是所使用的
Kernel版本；jffs2是文件系统，文件系统有2种，jffs2是可读写的，没有压缩，文件较大，squashfs是只读的，由于是压缩文件系统，
这意味着在相同大小的 Flash Rom 你可以安装更多软件；4MB是 Flash Rom
大小，这根据你使用的路由器版本而定，请参考刚才的路由器列表。下面是现时 OpenWrt提供的 Firmware：<br /><br />
[   ] openwrt-brcm-2.4-jffs2-4MB.trx          14-Sep-2005 19:21  2.1M  <br />
[   ] openwrt-brcm-2.4-jffs2-8MB.trx          14-Sep-2005 19:21  2.1M  <br />
[   ] openwrt-brcm-2.4-squashfs.trx           14-Sep-2005 19:21  1.5M  <br />
[   ] openwrt-motorola-jffs2-4MB.bin          14-Sep-2005 19:21  2.1M  <br />
[   ] openwrt-motorola-jffs2-8MB.bin          14-Sep-2005 19:21  2.1M  <br />
[   ] openwrt-motorola-squashfs.bin           14-Sep-2005 19:21  1.5M  <br />
[   ] openwrt-wrt54g-jffs2.bin                14-Sep-2005 19:21  2.1M  <br />
[   ] openwrt-wrt54g-squashfs.bin             14-Sep-2005 19:21  1.5M  <br />
[   ] openwrt-wrt54gs-jffs2.bin               14-Sep-2005 19:21  2.1M  <br />
[   ] openwrt-wrt54gs-squashfs.bin            14-Sep-2005 19:21  1.5M  <br />
[   ] openwrt-wrt54gs_v4-jffs2.bin            14-Sep-2005 19:21  2.1M  <br />
[   ] openwrt-wrt54gs_v4-squashfs.bin         14-Sep-2005 19:21  1.5M  <br /><br />
我用的是WRT54G v2.2版，所以我下载了
openwrt-wrt54gs-jffs2.bin，有了这文件后，我可以开始设定我的路由器了。WRT54G 默认的 IP 是
192.168.1.1，在接上你的电脑之前，你要更改你电脑的网络设定，把你电脑改为固定IP，IP是192.168.1.xxx，掩码是
255.255.255.0。然后用网络线把你的电脑和 WRT54G 其中一个 LAN 接口连起来，这时候你可以在 DOS PROMPT 中输入
“ping 192.168.1.1” 这命令，如果有回应的话就证明连线没有问题，如果出现 “Request Time Out”
，请检查一下你的防火墙和网线有没有问题（不要忘了为WRT54G接上电源）。<br /><br />
安装 OpenWrt 有几种方法，在不拆开路由器的情况下，最简单的方法是利用TFTP 软件，把整个 OpenWrt Firmware 更新到 WRT54G 的 Flash Rom里，<br />
现在请打开你的浏览器，在网址一栏输入“http://192.168.1.1”，这时候应该会出现一个登入画面，用户和密码都是“admin”，如果你
的路由器是新买回来的话，请先把WAN设定好，你可以随便给一个固定IP，但不要设定DHCP，因为如果WAN接口没有连线而且没有IP的话，接下来我们
的PING工具将无法使用，我们会利用“PING”工具的一个小BUG，更改[/url] WRT54G 的 BOOTWAIT 设定，让我们可以把
Firmware上传到TFTP服务器。操作如下：<br /><br />
1. 打开 ping工具，“administration” --&gt; “diagnostics” --&gt; “Ping”，又或者在网址一栏输入 “192.168.1.1/ping.asp”<br /><br />
2. 在 “IP Address”一栏中，顺序输入下面4行指令，每输入一行就按一下“PING”按钮：<br /><br /><br />
;cp${IFS}*/*/nvram${IFS}/tmp/n<br />
;*/n${IFS}set${IFS}boot_wait=on<br />
;*/n${IFS}commit<br />
;*/n${IFS}show&gt;tmp/ping.log<br /><br /><br />
当最后一行输入后，你会看到一堆文字，如果你看到其中一行是“boot_wait=on”的话，你可以继续下一步了。<br /><br />
3.  把你的 WRT54G 电源拔出来，然后准备好刚才的 Firmware，在Windows的DOS PROMPT，输入这条命令，但不要按 “ENTER”：<br /><br />
tftp -i 192.168.1.1 PUT C:\openwrt-wrt54gs-jffs2.bin<br /><br />
*这里，我把openwrt-wrt54gs-jffs2.bin放在 C:\ ，如果你放在别的位置，请按你的情况更改<br /><br />
4. 一边接上 WRT54G 的电源，同时另一边按  “ENTER” ，如果成功的话，你会看见 WRT54G上 的 DMZ 灯不停闪动，而且画面会出现类似下面的讯息：<br /><br />
Transfer successful: 1537024 bytes in 6 seconds, 256170 bytes/s<br /><br />
5. 等待 2-3 分钟后，DMZ 灯会停止闪动，这时执行 “telnet 192.168.1.1”，如果出现 OpenWrt 的欢迎画面，代表你安装成功了。<br /><br /><br /><br /><br />
Trying 192.168.1.1...<br />
Connected to 192.168.1.1.<br />
Escape character is '^]'.<br /><br />
BusyBox v1.00 (2004.12.24-03:19+0000) Built-in shell (ash)<br />
Enter 'help' for a list of built-in commands.<br /><br />
  _______                     ________        __<br />
 |       |.-----.-----.-----.|  |  |  |.----.|  |_<br />
 |   -   ||  _  |  -__|     ||  |  |  ||   _||   _|<br />
 |_______||   __|_____|__|__||________||__|  |____|<br />
          |__| W I R E L E S S   F R E E D O M<br /><br />
root@OpenWrt:/#<br /><br />
NVRAM 全名是 Non-Volatile Ram ，在 OpenWrt 里是用了 Flash Rom 最后的 64K 区块，用来储存一些环境参数，OpenWrt 通过这些参数来配置网络，DHCP，DNS和记载硬件版本等。<br /><br />
常用的 nvram 指令有以下 4 种：<br /><br />
1. nvram show<br />
列出 NVRAM 内所有参数，我们亦可以用 grep 命令来抽取部份资讯，例如<br /><br />
    nvram show | grep lan_<br /><br /><br />
这命令列出了所以用 lan_ 开头的参数，结果如下：<br /><br /><br />
    lan_gateway=192.168.1.254<br />
    dr_lan_rx=0<br />
    lan_netmask=255.255.255.0<br />
    lan_lease=86400<br />
    lan_stp=1<br />
    lan_hwaddr=00:12:17:E1:56:F5<br />
    lan_dns=211.152.179.7 202.96.128.86<br />
    lan_ifnames=vlan0 eth1<br />
    size: 12567 bytes (20201 left)<br />
    lan_ipaddr=192.168.1.1<br />
    lan_proto=static<br />
    lan_ifname=br0<br />
    lan_wins=<br />
    lan_hwnames=<br /><br />
2. nvram set 参数=数值<br />
用来添加或修改一些参数，例如我想把 LAN 的 IP 由 192.168.1.1 改为 192.168.1.2，可执行：<br /><br /><br />
    nvram set lan_ipaddr=192.168.1.2<br />
    nvram commit<br />
    reboot<br /><br /><br />
第 1 行是修改 IP 地址，第 2 行是保存，第 3 行是重新启动 OpenWrt ，因为更改 IP 地址后要重启才能生效。<br /><br />
3. nvram unset 参数<br />
用来删除一些参数，不过这个功能很少用到，因为 NVRAM 的 64K 容量足够保存大量参数，大部份人都赖得去删。<br />
例如我想删除 “dr_lan_rx=0” 这个参数，请执行：<br /><br />
    nvram unset dr_lan_rx<br /><br />
4. nvram commit<br />
当你对 NVRAM 做了一大堆修改后，你需要把这些修改保存起来，否则你的路由器 RESET 后，这些修改便没有了，和上面一样，这时你要执行：<br /><br />
    nvram commit<br /><br />
1. WRT54G 的网络概况<br /><br />
下面是 WRT54G 的内部结构示意图：<br /><br />
WRT54G由包括LAN，WAN，WIFI 等 3 部份组成，相等于图中的vlan0，vlan1，eth0。<br /><br /><a href="http://www.eosp.org/wp-content/photos/WRT54G_internal_architecture.png" target="_blank">http://www.eosp.org/wp-content/photo...chitecture.png</a><br /><br />
当你安装好 OpenWrt 后，NVRAM 里的默认配置是这样的：<br /><br /><br />
    lan_ifname=br0<br />
    lan_ifnames=”vlan0 eth1”<br />
    lan_proto=static<br />
    lan_ipaddr=192.168.1.1<br />
    lan_netmask=255.255.255.0<br /><br />
    wan_ifname=vlan1<br />
    wan_proto=dhcp<br /><br />
第 1 项 lan_ifname=br0 是指 LAN 的网络介面名称；<br />
第 2 项 lan_ifnames=”vlan0 eth1” 是指实际上 LAN 的真正网络介面，这里包括 vlan0(Port 1-4) 和 eth1 (无线网卡接口) ；<br />
第 3 项 lan_proto=static 是指 LAN 用固定 IP 方式；<br />
第 4 项 lan_ipaddr=192.168.1.1 指定了 LAN 的 IP 是 192.168.1.1；<br />
第 5 项 lan_netmask=255.255.255.0 指定了 LAN 的子网络掩码；<br /><br />
第 6 项 wan_ifname=vlan1 指定了 WAN 的网络为 vlan1 (Port 0)；<br />
第 7 项 wan_proto=dhcp 指定了 WAN 的网络方式为 DHCP；<br /><br />
2. 配置 Lan 网络参数<br />
假设我想修改路由器的 TCP/IP 设定为:<br /><br />
IP: 192.168.0.1<br />
掩码: 255.255.255.0<br />
网关: 192.168.0.254<br />
DNS1: 192.168.0.254<br />
DNS2: 202.14.67.4<br /><br />
并打开 DHCP 服务，IP 范围由 192.168.0.100 至 192.168.0.150；可以执行以下命令:<br /><br /><br />
    nvram set lan_proto=static<br />
    nvram set lan_ipaddr=192.168.0.1<br />
    nvram set lan_netmask=255.255.255.0<br />
    nvram set lan_gateway=192.168.0.254<br />
    nvram set lan_dns=’192.168.0.254 202.14.67.4’<br /><br />
    nvram set dhcp_start=100<br />
    nvram set dhcp_num=50<br />
    nvram commit<br />
    reboot<br /><br />
第 1 项 nvram set lan_proto=static 是指 LAN 的网络方式为固定 IP<br />
第 2 项 nvram set lan_ipaddr=192.168.0.1 是指定 LAN 的 IP 地址为 192.168.0.1<br />
第 3 项 nvram set lan_netmask=255.255.255.0 是指定 LAN 的子网络掩码为 255.255.255.0<br />
第 4 项 nvram set lan_gateway=192.168.0.254 是指定 LAN 的网关为 192.168.0.254<br />
第 5 项 nvram set lan_dns=’192.168.0.254 202.14.67.4’ 是指定 LAN 使的 DNS 服务器，由于DNS服务器有 2 个，所以用空格来分开。<br /><br />
第 6 项 nvram set dhcp_start=100 是指 DHCP 服务器从 192.168.0.100 开始派发 IP<br />
第 7 项 nvram set dhcp_num=50 是指 DHCP 从 192.168.0.100 开始 派发到 192.168.0.150 (100+50) 为止。<br /><br />
3. 设定WAN<br />
一般常见的上网方式有3种: DHCP, PPPOE 拨号上网 及 STATIC IP(固定 IP)<br /><br />
2.1 DHCP<br />
DHCP很简单，你只需告诉路由器用DHCP来上网，它便会替你自动取得IP，网络掩码，网关，DNS等资料<br /><br /><br />
    nvram set wan_proto=dhcp<br />
    nvram commit<br />
    reboot<br /><br />
2.2 固定 IP<br />
很多商用宽带都是使用固定 IP，ISP 会提供 IP 地址（第2项），子网络掩码（第3项），网关（第4项）及DNS（第5项）资料，DNS如果超过一个的话用空格分开。<br /><br /><br />
    nvram set wan_proto=static<br />
    nvram set wan_ipaddr=218.103.124.24<br />
    nvram set wan_netmask=255.255.255.252<br />
    nvram set wan_gateway=218.103.124.23<br />
    nvram set wan_dns=’210.80.60.1 210.80.60.2’<br />
    nvram commit<br />
    reboot<br /><br />
2.3 PPPOE<br />
PPPOE 在家用宽带是很常见的，ISP会提供 用户名及密码，你只需把下面第5和第6项换成相应的用户名及密码就可以用PPPOE上网了。<br /><br /><br />
    nvram set wan_ifname=ppp0<br />
    nvram set wan_proto=pppoe<br />
    nvram set ppp_mtu=1492<br />
    nvram set pppoe_ifname=vlan1<br />
    nvram set ppp_username=your_isp_login<br />
    nvram set ppp_passwd=your_isp_password<br />
    nvram commit<br />
    reboot<br /><br />
第 1 项 nvram set wan_ifname=ppp0 是指 WAN 使用 ppp0 网络介面来拨号上网<br />
第 2 项 nvram set wan_proto=pppoe 是指 WAN 使用 PPPOE 的方式上网<br />
第 3 项 nvram set ppp_mtu=1492 指定 MTU 为 1492<br />
第 4 项 nvram set pppoe_ifname=vlan1 指 PPPOE 拨号的介面是 vlan1<br />
第 5 项 nvram set ppp_username=your_isp_login 指定PPPOE 的用户名是 your_isp_login<br />
第 6 项 nvram set ppp_passwd=your_isp_password 指定了 PPPOE 的密码是 your_isp_password<br /><br />
4. 配置无线网络<br /><br /><br />
    nvram set wl0_gmode=<br />
    nvram set wl0_ssid=<br />
    nvram set wl0_channel=<br />
    nvram set wl0_closed=<br />
    nvram commit<br />
    wifi up<br /><br />
关闭 WEP 和 WPA<br /><br /><br />
    nvram set wl0_wep=disabled<br />
    nvram set wl0_akm=open<br /><br />
开启WEP<br /><br />
    nvram set wl0_wep=<br />
    nvram set wl0_wep_bit=<br />
    nvram set wl0_key=<br />
    nvram set wl0_key1=<br />
    nvram set wl0_key2=<br />
    nvram set wl0_key3=<br />
    nvram set wl0_key4=<br />
    nvram set security_mode_last=wep<br />
    nvram commit<br />
    ifdown wifi<br />
    ifup wifi<br /><br />
WPA<br /><br /><br />
    nvram unset wl0_auth_mode<br />
    nvram set wl0_akm=psk<br />
    nvram set wl0_crypto=<br />
    nvram set wl0_wpa_psk=<br />
    nvram set wl0_radius_key=<br />
    nvram set wl0_radius_ipaddr=<br />
    nvram set wl0_radius_port=<br />
    nvram set security_mode_last=wpa<br />
    nvram commit<br /><br />
无线网络 – MAC Filter<br /><br /><br />
    nvram set wl0_macmode=allow<br />
    nvram set wl0_mac_list=<br />
    nvram set wl0_mac_deny=<br />
    nvram commit<br />
    wifi up<br /><br />
5. 加强 OpenWrt 的安全性<br />
我认为没有密码和使用 Telnet 是不安全的，OpenWrt 在设定密码后会把 Telnet 关闭，改用 SSH 服务<br /><br /><br />
    passwd<br /><br />
ipkg 是 OpenWrt 内的一个软件安装管理工具，在 OpenWrt 内输入<br /><br />
    root@Linksys:~# ipkg<br /><br /><br />
你会得到 ipkg 的说明和帮助，接下来我会说明 ipkg 常用的几个命令：<br /><br />
1. ipkg update<br />
ipkg 会到 <a href="http://downloads.openwrt.org/whiterussian/packages/" target="_blank">http://downloads.openwrt.org/whiterussian/packages/</a> 下载并更新最新的软件包列表(这个列表的位置在/etc/ipkg.conf指定)：<br /><br /><br />
    root@Linksys:~# ipkg update<br />
    Downloading <a href="http://downloads.openwrt.org/whiterussian/packages/Packages" target="_blank">http://downloads.openwrt.org/whiteru...kages/Packages</a><br />
    Updated list of available packages in /usr/lib/ipkg/lists/whiterussian<br />
    Downloading <a href="http://downloads.openwrt.org/whiterussian/packages/non-free/Packages" target="_blank">http://downloads.openwrt.org/whiteru...-free/Packages</a><br />
    Updated list of available packages in /usr/lib/ipkg/lists/non-free<br />
    Successfully terminated.<br /><br />
2. ipkg list<br />
在更新之后，我们可以用 ipkg list 这命令查看一下有什么软件包可供安装，这里我会列出部份结果：<br /><br /><br />
    root@Linksys:~# ipkg list<br />
    aiccu – 2005.01.31-1 – SixXS Automatic IPv6 Connectivity Client Utility<br />
    arptables – 0.0.3-1 – ARP firewalling software<br />
    arpwatch – 2.1a11-1 – Ethernet monitor program for keeping track of ethernet/ip address pairings<br />
    asterisk – 1.0.7-1 – An open source PBX<br />
    ...<br /><br />
3. ipkg install<br />
安装软件包，有 2 种方法，例如我想安装 OpenSSH 的 SFTP 服务器(注 1)，方便我以后上传文件到 OpenWrt，我可以执行 ipkg list 或到 OpenWrt 的软件包网址取得软件 SFTP 服务器的资料：<br /><br />
Package: openssh-sftp-server<br />
Version: 4.0p1-1<br />
Depends: zlib, libopenssl<br />
Section: net<br />
Architecture: mipsel<br />
Maintainer: <a href="mailto:bugs@openwrt.org">bugs@openwrt.org</a><br />
MD5Sum: 145c72f82f2404b991a96bf5f3ef2262<br />
Size: 14086<br />
Filename: openssh-sftp-server_4.0p1-1_mipsel.ipk<br />
Source: buildroot internal<br />
Description: OpenSSH SFTP server<br /><br />
之后我可以选择第 1 个方法用软件包名来安装，这方法会自动把软件包下载并安装：<br /><br />
    ipkg install openssh-sftp-server<br /><br />
或者选择第 2 个方法从网站把安装包下载到路由器上，然后输入文件名安装：<br /><br />
    ipkg install openssh-sftp-server_4.0p1-1_mipsel.ipk<br /><br />
4. ipkg list_installed<br />
这个命令会列出 OpenWrt 预先为你安装好的软件 (包括一些常用软件和驱动) 以及你后来安装的软件。<br /><br />
5. ipkg remove<br />
当你的空间不足时，这个命令非常有用，你先执行 ipkg list_installed 得出己安装的软件列表，然后找出你要删除的软件包名称，例如：<br /><br />
    ipkg remove openssh-sftp-server<br /><br />
注意事项：<br />
由于 WRG54G 的空间有限，安装软件时要留意软件的大小和剩余的空间，我们可以用 df -h 命令得知 Flash Rom 和 虚拟内存的使用量：<br /><br />
    root@Linksys:~# df -h<br /><br />
Filesystem                Size      Used Available Use% Mounted on<br />
/dev/root                 3.2M      2.8M    372.0k  89% /<br />
none                      7.0M      6.5M    540.0k  92% /tmp<br />
/dev/mmc/disc0/part1     14.2M      7.5M      6.6M  53% /sd<br /><br />
结果显示我的 WRT54G 只剩下 372k 的空间，虚拟内存也只剩下 540k，因为我为我的WRT54G 加装了一张 16MB 的 SD Card，所以你会看到有一项设备 /dev/mmc/disc0/part1 剩余 6.6M 空间。<br /><br />
注 1： 安装了 openssh-sftp-server，你会发现 sftp 服务器并不能正常使用，为什么呢？！这时你要输入这个命令：<br /><br />
    ln -s /usr/libexec /usr/lib<br /><img src ="http://www.cppblog.com/Khan/aggbug/15573.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.cppblog.com/Khan/" target="_blank">Khan</a> 2006-11-23 10:02 <a href="http://www.cppblog.com/Khan/archive/2006/11/23/15573.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss>