Intelligence without ambition is a bird without wings.

2015-03-26
C-函数操作结果返回方式

通过返回值

直接值传递

优点

简单,快捷,不存在内存溢出

缺点

  • 不能返回错误代码

  • 无法返回非内置数据类型

适用范围

  • 返回简单的内置类型数据

  • 出错少或错误不是很严重

实例

size_t strlen(const char * str);

内部分配static类型数据,返回指针

优点

  • 可返回非内置数据类型

  • 调用方便,调用者无需手动分配内存

缺点

  • 不可重入

  • 非线程安全

实例

char *inet_ntoa(struct in_addr);

通过参数

调用者分配内存,需要传入缓冲区大小

优点

  • 可返回非内置数据类型

  • 可重入

  • 线程安全

  • 正确操作下,内存不会溢出(通过缓冲区大小参数)

缺点

  • 调用麻烦,需要手动分配内存

实例

char* fgets(char *str, int num, FILE * stream);

调用者分配,不传入缓冲区大小(自己不采用,只是存在此种接口)

优点

  • 可返回非内置数据类型

  • 可重入

  • 线程安全

缺点

  • 存在缓冲区越界风险!

实例

char * gets ( char * str );

二次调用确定所需空间

优点

  • 可以返回调用者不能确定的内存空间的数据

缺点

  • 二次调用,使用麻烦

实例

DWORD GetAdaptersInfo(_Out_    PIP_ADAPTER_INFO pAdapterInfo, _Inout_  PULONG pOutBufLen);

参考

  1. GetAdaptersInfo.aspx)
阅读此文

2015-03-26
extern "C"

作用

当使用C++编译器对C++源码编译时,对C函数采用”C”语言方式编译和连接(函数导出名不变)

为什么需要extern "C"

因为C++支持函数重载,所以对函数名存在修饰操作。

若一个函数为普通全局函数,制作为dll,其他C程序进行调用,当编译该程序采用C编译器,无法找到该符号,因为C编译器与C++编译器对函数名的修饰规则不一致!

所以为了使C编译器能够使用这些函数,需要使用extern "C"声明。

惯用法

1
2
3
4
5
6
7
8
9
#ifdef __cplusplus
extern "C" {
#endif

...

#ifdef __cplusplus
}
# endif
阅读此文

2015-03-26
采用doxygen的项目列表

  • log4cpp
阅读此文

2015-03-26
使用宏控制dll导入或导出

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
#pragma once

#ifdef XXX_HAS_DLL
# ifdef XXX_BUILD_DLL
# if defined(_MSC_VER) || defined(__BORLANDC__) || defined(__MINGW32__)
# define LOG4CPP_EXPORT __declspec(dllexport)
# else
# define LOG4CPP_EXPORT
# endif
# else
# if defined(_MSC_VER) || defined(__BORLANDC__) || defined(__MINGW32__)
# define LOG4CPP_EXPORT __declspec(dllimport)
# else
# define LOG4CPP_EXPORT
# endif
# endif
#else
# define XXX_EXPORT
#endif

说明:

  • XXX为库名称

  • XXX_HAS_DLL 编译器是否支持__declspec(dllexport)

  • XXX_BUILD_DLL 动态库内部使用,还是供外部引用

  • XXX_EXPORT 用来说明某个变量,函数,类是否为导出或导入

参考

  1. log4cpp/include/Export.hh
  2. https://gcc.gnu.org/wiki/Visibilit
阅读此文

2015-03-26
log4cpp

简介

一个C++日志库,模仿Log4j(java日志库)

优点

  • 可拓展的、多种记录日志方式,包括命令行、文件、回滚文件、内存、syslog服务器、
    win事件日志、VS debuger等

  • 可动态调整日志优先级

  • 可动态加载配置文件

  • 内存占用小,不到200KB

  • 跨平台

原理

log4cpp主要有3大组件:category、appender、layout。

  • layout

    用来控制输出日志消息的格式,每个appender关联一个layout

  • appender

    用来指定输出目的地

  • category

    一个日志工作体,具有日志级别属性,可以拥有多个appender(一条消息可以输出到多个目的地)

    category被组织成一棵树,子category创建时优先级缺省NOTSET,category缺省会继承父category的appender。
    而如果不希望这种appender的继承关系,log4cpp允许使用additivity 标签,为false时新的appender取代category的appender列表。

使用流程

  1. 实例化一个layout对象,设置格式

  2. 实例化一个appender对象,设置layout

  3. 实例化一个category,添加appender

参考

  1. http://log4cpp.sourceforge.net/
  2. 便利的开发工具-log4cpp快速使用指南
阅读此文

2015-03-25
cmake-常用命令

  • 修改目标输出文件名

    SET_TARGET_PROPERTIES(<target_name> PROPERTIES OUTPUT_NAME <new_name>)
    
阅读此文

2015-03-24
windows-获取当前进程文件名

阅读此文

2015-03-23
syslinux-memdisk

作用

启动一些软盘镜像,硬盘镜像,ISO镜像。

如何使用

memdisk作为kernel,而那些镜像文件作为初始化文件系统(initrd)

镜像文件(zip或gzip格式)作为INITRD命令的参数传递

  • 命令行方式

    memdisk initrd=hdt.img

  • 配置文件方式

    # Boot Hardware Detection Tool from floppy image
    LABEL hdt_floppy
    LINUX memdisk
    INITRD hdt.img
    
    # Boot Hardware Detection Tool from iso image (with 'iso' parameter)
    LABEL hdt_iso
    LINUX memdisk
    INITRD hdt.iso
    APPEND iso
    
    # Boot DOS from floppy image (with 'raw' parameter)
    LABEL dos_floppy_with_raw
    LINUX memdisk
    INITRD dosboot.img
    APPEND raw
    

参考

  1. http://www.syslinux.org/wiki/index.php/MEMDISK
阅读此文

2015-03-20
syslinux

syslinux安装

  • 安装时,会将ldlinux.c32,ldlinux.sys拷贝到安装目录,默认为boot/syslinux/
    可以使用--directory -d Directory for installation target指定

    syslinux安装的分区上的PBR会根据安装目录查找ldlinux.c32,并将该目录作为根目录

syslinux引导过程

  • MBR加载活动分区PBR

  • PBR根据安装时指定的安装目录,查找ldlinux.c32,若找不到,则到根目录查找

  • 查找读取syslinux.cfg

  • 进入菜单交互

syslinux文件说明

| 文件名 | 功能 | 依赖 |
|————–+—————————–+————————–|
| ldlinux.c32 | 查找、解析syslinux.cfg | |
| libutil.c32 | 功能库 | |
| libcom32.c32 | 核心功能库 | |
| vesamenu.c32 | 菜单功能 | libutil.c32,libcom32.c32 |
| splash.jpg | 图片背景 | |
| syslinux.cfg | 启动配置文件 | |
| chain.c32 | 链式加载 | |
| memdisk | memdisk命令,虚拟内存磁盘 | |
| hdt.c32 | 硬件检测工具 | libmenu.c32,libgpl.c32 |
| linux.c32 | linux命令 | |

note

  • 启动ISO镜像

    因为image都是通过虚拟设备(虚拟软盘,虚拟光驱),由BIOS 13号中断来访问的,
    所以当操作系统加载完设备驱动时,它将自己去访问设备,不再通过BIOS去访问,
    这时虚拟设备将失效,报错INT 13h access: Not all images will complete the boot process!

参考

  1. http://www.syslinux.org/wiki/index.php/Syslinux_5_Changelog
  2. http://www.syslinux.org/wiki/index.php/Library_modules
  3. http://linux.die.net/man/1/syslinux
  4. http://www.syslinux.org/wiki/index.php/SYSLINUX
  5. http://www.syslinux.org/wiki/index.php/Boot_an_Iso_image
  6. http://www.syslinux.org/wiki/index.php/MEMDISK#INT_13h_access:_Not_all_images_will_complete_the_boot_process.21
  7. http://www.syslinux.org/wiki/index.php/MEMDISK
阅读此文

2015-03-20
活动分区

活动分区,是MBR主分区中的一种,目的是为了标识哪个分区是启动分区。

在boot loader stage 1阶段,将检查DPT中是否有唯一活动分区,若存在,则载入执行该分区的VBR。

特点

  • 每个磁盘只能有一个活动分区

  • 只能将主分区设置为活动分区,不能将逻辑分区设为活动分区

设置,取消活动分区

  • 使用diskmgmt.msc

  • diskpart

    • cmd中运行diskpart

    • 列出当前磁盘

      list disk
      
    • 选择要操作的磁盘

      select disk X
      
    • 列出分区

      list partition
      
    • 选择要操作的分区

      select partition X
      
    • 标记为活动分区

      active
      
    • 标记为非活动分区

      inactive
      

参考

阅读此文