• setjmp与longjmp非局部跳转函数的使用


    [root@bogon code]# cat c.c
    #include<stdio.h>
    #include<setjmp.h>
    static jmp_buf env;//定义全局变量env
    void job()
    {
        longjmp(env,2);//会返回到setjmp(env)处,且返回值为2
    }
    void work(int argc)
    {
        if(argc==1)//没有参数
            longjmp(env,1);//返回到setjmp(env)处,返回值为1
        job();//有参数调用job()
    }
    int main(int argc,char *argv[])
    {
        switch(setjmp(env))//setjmp(env)初始值为0
        {
            case 0:
                work(argc);//传参数个数过去,argc为1代表没有参数
                break;
            case 1:
                printf("this is from no parameter work()
    ");//不带程序参数的输出
                break;
            case 2:
                printf("this is from have parameter job()
    ");//带程序参数的输出
                break;
        }
        return 0;
    }
    [root@bogon code]# gcc c.c
    [root@bogon code]# ./a.out
    this is from no parameter work()
    [root@bogon code]# ./a.out 32
    this is from have parameter job()
    [root@bogon code]# 
    

    这里写图片描述
    现在我们来看一下优化编译器问题

    [root@bogon code]# cat c.c
    #include<stdio.h>
    #include<stdlib.h>
    #include<setjmp.h>
    static jmp_buf env;
    void work(int a,int b,int c)
    {
        longjmp(env,1);
    }
    int main(int argc,char *argv[])
    {
        int a;
        register int b;
        volatile int c;//将变量声明为volatile,那么编译优化时,该变量的值(300)不会在调用longjmp函数后,重置为setjmp函数调用前的值(30),而其他类型的变量都会重置
        a=10;
        b=20;
        c=30;
        if(setjmp(env)==0)
        {
            a=100;
            b=200;
            c=300;
            work(a,b,c);
        }
        else
            printf("a is %d
    b is %d
    c is %d
    ",a,b,c);
        return 0;
    }
    [root@bogon code]# gcc c.c//没有进行编译优化,所以都没有重置
    [root@bogon code]# ./a.out
    a is 100
    b is 200
    c is 300
    [root@bogon code]# gcc -O c.c//使用选项-O进行编译优化,所以有重置
    [root@bogon code]# ./a.out
    a is 10
    b is 20
    c is 300
    [root@bogon code]# 

    为了使程序便于维护,还是应当尽量避免使用setjmp和longjmp,不过有时候在恰当的地方,其用处还是很大的,另外我们还应该限制使用goto一样

  • 相关阅读:
    python模拟android屏幕高频点击工具
    android adb shell and monkey 学习记录
    appium+python环境搭建
    python监控接口请求
    JetBrains Pycharm 破解+汉化
    loadrunner调用jar包方法
    python抢小米6自动化脚本
    CDlinux制作U盘启动盘,打造自己的口袋系统
    无线渗透测试之wifi密码破解
    测试-test1
  • 原文地址:https://www.cnblogs.com/biaopei/p/7730627.html
Copyright © 2020-2023  润新知