最近学习网络层协议的时候,注意到了IP协议中数据包分片的问题。下图是IP协议头的数据字段的示意:

如图所示,IP协议理论上允许的最大IP数据报为65535字节(16位来表示包总长)。但是因为协议栈网络层下面的数据链路层一般允许的帧长远远小于这个值,例如以太网的MTU(即Maximum Transmission Unit,最大传输单元)通常在1500字节左右。所以较大的IP数据包会被分片传递给数据链路层发送,分片的IP数据报可能会以不同的路径传输到接收主机,接收主机通过一系列的重组,将其还原为一个完整的IP数据报,再提交给上层协议处理。上图中的红色字段便是被设计用来处理IP数据包分片和重组的。

那么,这三个字段如何实现对分片进行表示呢?

Read More

cJSON是一个超轻巧,携带方便,单文件,简单的可以作为ANSI-C标准的Json格式解析库。

那什么是Json格式?这里照搬度娘百科的说法:

Json(JavaScript Object Notation) 是一种轻量级的数据交换格式。它基于JavaScript(Standard ECMA-262 3rd Edition – December 1999)的一个子集。JSON采用完全独立于语言的文本格式,但是也使用了类似于C语言家族的习惯(包括C, C++, C#, Java, JavaScript, Perl, Python等)。这些特性使JSON成为理想的数据交换语言。易于人阅读和编写,同时也易于机器解析和生成。

更加详细的解释和示例请查看 http://www.json.org/ 主页。

其实简单说,Json就是一种信息交换格式,而cJSON其实就是对Json格式的字符串进行构建和解析的一个C语言函数库。

可以在这个地址下载到cJSON的源代码: http://sourceforge.net/projects/cjson/

__MACOSX目录是在Mac OSX系统下打包引入的临时目录,无视它。

简单的阅读下README文件,先学习cJSON库的使用方法。若是连库都还不会使用,分析源码就无从谈起了。通过简单的了解,我们得知cJSON库实际上只有cJSON.c和cJSON.h两个文件组成,绝对轻量级。

不过,代码风格貌似有点非主流,先用indent格式化一下代码吧。我个人喜欢K&R风格的代码,使用的indent命令行参数如下:

1
indent -bad -bli 0 -ce -kr -nsob --space-after-if --space-after-while --space-after-for --use-tabs -i8

Read More

Go语言简介

Go语言(golang)是Google推出的一种全新的编程语言,可以在不损失应用程序性能的情况下降低代码的复杂性。Google首席软件工程师罗布派克(Rob Pike)说:我们之所以开发Go,是因为过去10多年间软件开发的难度令人沮丧。

Go语言的主要特性:

  • 编译型语言,执行效率接近c/c++
  • 自动垃圾回收
  • 更丰富的内置类型和自动类型推导(类似c++11的auto)
  • 函数可以返回多个值
  • 拥有更好的错误处理
  • 匿名函数和闭包
  • 支持类型和接口
  • 并发编程
  • 支持反射机制
  • 语言交互性强
  • 工程依赖自动推导
  • 打包和部署容易
  • ……

就我个人而言,感觉Go语言是对像是对c语言的修补和延伸。这个由一群工程师们设计出的语言实在太符合我的口味了,所有的特性都是为了解决实际问题而存在的。但是新增加的特性并没有给语言带来额外的负担,相反,Go的语法反而很简单。大道至简,这是我喜欢Go的原因。

Go语言开发环境部署

这个相信大家很容易在网上就能获取到下载和安装的教程,就不赘述了。

Read More

§ 1 线程安全的对象生命期管理

  • 对象的生与死不能由对象自身拥有的mutex(互斥器)来保护。如何避免对象析构时可能存在的race condition(竞态条件)是C++多线程编程面临的基本问题。

  • 当一个对象被多个线程同时看到,那么对象的销毁时机就会模糊不清,可能出现多种的race condition(竞态条件):

    • 即将析构一个对象时,从何而知此刻是否有别的对象正在执行该对象的成员函数?
    • 如何保证在执行成员函数期间,对象不会被另一个线程所析构?
    • 在调用某个对象的成员函数之前,如何得之这个对象还活着?它的析构函数是否会碰巧执行到一半?
  • 一个线程安全的class应当满足下面三个条件:

    • 多个线程同时访问时,其表现出正确的行为。
    • 无论操作系统如何调度这些线程,无论这些线程的执行顺序如何交织(interleaving)。
    • 调用端代码无需额外的同步或其它协调动作。
  • 按照以上定义,C++标准库中的大多数类都不是线程安全的,包括std:string、std::vector、std::map等,这些class通常需要在外部加锁才能供多个线程同步访问。

Read More