Linux管道函数使用

背景:项目有个功能是查看版本号(像什么内核版本号、驱动版本号,等等),是通过管道来实现的,网上也有这方面的介绍,就不多说了。
在一次测试过程中,发现不断查看版本号竟然会导致系统复位(比如查看20次、40次、100次),这个bug发现晚的原因是没有谁那么无聊连续查看100次版本号,当然,发现也是碰巧在几次查看之后系统就挂了。后来发现是因为某个地方卡住导致某个线程超时而复位。后来跟踪到了这个管道函数中来。解决的方法是使用读取文件的方法来获取系统版本号(如内核版本)。不过真正原因还没有找到,可能出在popen这类函数中。
下面给出示例代码:

#include <stdio .h>
#include <stdlib .h>
#include <string .h>
#include <unistd .h>
#include <signal .h>

static  void OnSignal( int signalno)
{
    printf( "receive signal num: %d\n", signalno);
     int bExit = true;
     for ( int i =  0; i <  100; i++)
    {
         if (signalno ==  17 || signalno ==  13)
        {
            bExit = false;
             break;
        }
    }
     if (bExit)
    {
        printf( "exit process.\n");
    }
}

// 通过管道读取执行命令后的信息
void GetSystemCmdInfo( const  char* cmd,  char* buf,  int len)
{
     char info[ 256] = { 0};

    FILE* fp = popen(cmd,  "r");
     if (fp)
    {
        fread(info,  1sizeof(info), fp);

         if ( buf != NULL && len > ( int)strlen(info) )
        {
            strcpy(buf, info);
        }
        pclose(fp);
    }
}

// 通过文件读取到信息
// 这种方法是读文件,上面的方法是执行命令,两者不是一回事
void ReadKernelVersion( char* file,  char* buf,  int len)
{
    FILE* fp = NULL;
     char info[ 256] = { 0};
    fp = fopen(file,  "r");
     if (fp == NULL)
    {
        perror( "open file error");
         return;
    }
    fread(info,  1sizeof(info), fp);
     if ( buf != NULL && len > ( int)strlen(info) )
    {
        strcpy(buf, info);
    }
    fclose(fp);
}

int main( void)
{
     char szValue[ 512] = { 0};
     char buf[ 1024] = { 0};
     int iLen =  0;
     for ( int i =  0; i <  255; i++)
    {
         if (i != SIGILL && i != SIGBUS && i != SIGSEGV)
        {
            signal(i, OnSignal);
        }
    }
     // 执行此函数时,会有SIGCHLD信号
    GetSystemCmdInfo( "cat /proc/version", szValue,  sizeof(szValue));
     //ReadKernelVersion("/proc/version", szValue, sizeof(szValue));
    iLen = sprintf(buf,  "[Kernel ver]: %s\r\n", szValue);
    printf( "%s", buf);

     return  0;
}

popen算是重型武器了,一般的小场合可不必使用,像查看内核版本,可能使用cat /proc/version命令,也可以读取/proc/version文件。
还是那名话说得好,具体情况具体分析,因地制宜采用不同的策略方能制胜。


语法高亮由迟思堂工作室强力支持

声明:本文仅为学习之目的,代码仅是示例性代码,网络上也能找到类似用法,无意亦无胆涉及过多其它代码。
                                                                                                                                                                                                                  李迟 代码随笔 即日

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值