求教一个关于C语言数据溢出的检验程序有关问题和setjmp函数,有代码

求教一个关于C语言数据溢出的检验程序问题和setjmp函数,有代码
最近在做毕设,课题是解决编译器对于数据溢出不报错的问题的解决办法,也就是说要设计一个算法或者流程,当在运算中(打比方,两个向量的相加相减和内积的运算)出现数据溢出的时候,程序能检测出来,然后提示并报错。

我根据课内的目标写了一小段代码,用到了C语言的跳转,setjmp()和longjmp(),可是遇到了一些小小的问题,特来请教有经验的前辈。

//
//  main.c
//  Bachelorarbeit
//
//  Created by Nan on 1/1/14.
//  Copyright (c) 2014 Nan. All rights reserved.
//

#include <stdio.h>
#include <setjmp.h>

jmp_buf jump_buffer;

typedef struct Vektor{
    short int x,y,z;
}Point,*pPoint;

void Input(pPoint p)
{
    printf("please enter the value of x :");
    scanf("%hd",&(p->x));
    printf("please enter the value of y :");
    scanf("%hd",&(p->y));
    printf("please enter the value of z :");
    scanf("%hd",&(p->z));
}


//Skalarprodukt
double Inner(Point p1,Point p2)
{
    return p1.x*p2.x+p1.y*p2.y+p1.z*p2.z;
}

//Addition
void Add(Point p1,Point p2,Point *p3)
{
    p3->x=p1.x+p2.x;
    p3->y=p1.y+p2.y;
    p3->z=p1.z+p2.z;
}

//Subtraktion
void Subtra(Point p1,Point p2,Point *p4)
{
    p4->x=p1.x-p2.x;
    p4->y=p1.y-p2.y;
    p4->z=p1.z-p2.z;
}

void show_point(Point p)
{
    printf("(%.3d,%.3d,%.3d)", p.x, p.y, p.z);
}

int main()
{

    Point p1, p2, p3,p4;
    
    if (setjmp(jump_buffer)==0) {
        printf("\n*******input p1*******\n"), Input(&p1);
        printf("\n*******input p2*******\n"), Input(&p2);
        Add(p1, p2, &p3);
        Subtra(p1, p2, &p4);
        if(p3.x!=(p1.x+p2.x)){
            longjmp(jump_buffer, 1);
        }
        puts("\n=======result=======");
        printf("\ninner: %.3lf", Inner(p1, p2));
        printf("\nadd:"), show_point(p3);
        printf("\nmin:"), show_point(p4);

    }
    else{
        printf("\n*******the result is overflow,pleas check your input and enter the value again*******\n"); 
    }
    
    while(getchar()!='\n');
    puts("\npress enter to exit.\n");
    getchar();
    return 0;
}


我用的是short类型,范围是-326767到32767,然后运行实例如下

求教一个关于C语言数据溢出的检验程序有关问题和setjmp函数,有代码

当两个向量相加时,32767+1结果时-32767,得到的P3点的响应值跟真正的32768不对应,会进入longjmp的跳转部分,但是跳转完之后我那个the result is overflow那个输出就进入无限循环了,也就是不停的输出,想请教是什么原因。 还有就是关于数据溢出的检测,我这么做有没有问题?涉及到向量的内积,也就是两点相乘的时候出现溢出,要如何检测?十分感谢。

------解决方案--------------------
太谢谢你了,例子十分清楚,容我追加一个问题,就是乘法的溢出,代码中我没有处理乘法部分是因为我还没弄明白如何处理他们?你有好的建议吗?尤其是对于带符号的向量,内积中可能会有一部分的乘法结果溢出,但是有负值的话,最后求得的内积的和还是有可能在范围内,导致加减法溢出的检验方法不适用。

===============
一样啊。用一个更大的类型,比如int, 如果计算的结果超出了short的范围,则溢出。代码几乎一模一样,两overflow函数都是重用的。
void Multiply(Point p1, Point p2, Point* rslt)
{
   int x=(int)p1.x*p2.x;
   int y=(int)p1.y*p2.y;
   int z=(int)p1.z*p2.z;

   if(overflow(x) 
------解决方案--------------------
 overflow(y) 
------解决方案--------------------
 overflow(z))
       longjmp(jump_buffer, 3); // suppose we decide to differentiate MULTIPLY overflow