ตัวอธิบายไฟล์ไม่ถูกต้องในฟังก์ชัน recvfrom

นี่คือโค้ดฝั่งเซิร์ฟเวอร์ของฉันสำหรับ udp

#include"headers.h"
int main(int argc,char **argv)
{
    //------------udp server socket connection------//

    int sd1;
    struct sockaddr_in serveraddr, clientaddr;
    char buffer[100];
    char *bufptr = buffer;
    int cnt=1,ret;
    socklen_t clen;
    clen=sizeof(clientaddr);

    //int buflen = sizeof(buffer);

    sd1=socket(AF_INET,SOCK_DGRAM,0);

    printf("udp socket id=%d\n",sd1);

    printf("socket created for udp..\n");

    if(sd1<0)
    {
        perror("udp_sfd");
        exit(0);
    }

    printf("server socket created..\n");

    serveraddr.sin_family=AF_INET;
    serveraddr.sin_port=htons(atoi(argv[1]));
    serveraddr.sin_addr.s_addr=INADDR_ANY;

    if(bind(sd1,(struct sockaddr *)&serveraddr,sizeof(serveraddr))<0)
    {
        perror("bind\n");
        exit(0);
    }
    else
    {

        while(1)
        {
            printf("server accept from client\n");

            ret=recvfrom(sd1,(char *)bufptr,strlen(buffer),0,(struct sockaddr *)&clientaddr,&clen);
            printf("ret=%d\n",ret);

            //printf("hello\n");
            if(ret<0)
            {
                perror("recvfrom");
                exit(0);
            }
            else
            {
                printf("UDP Server received the following:\n \"%s\" message\n", bufptr);
            }
            //close(sd1);
        }
    }

    close(sd1);
    return 0;
}

ฉันกำลังส่งบัฟเฟอร์จากฝั่งไคลเอ็นต์... และในฝั่งเซิร์ฟเวอร์ มันทำให้ฉันมีข้อผิดพลาดเช่นนี้....

file descriptor ไม่ดี .... ฉันควรทำอย่างไร...

ฉันเปลี่ยนชื่อ file descriptor 2 ครั้งแล้ว...ก็ยังใช้งานไม่ได้...


person Milan Shah    schedule 21.10.2016    source แหล่งที่มา


คำตอบ (3)


recvfrom ของคุณไม่ดี แทนที่จะใช้ strlen(buffer) คุณควรใช้ sizeof(buffer) เนื่องจากบัฟเฟอร์อยู่บนสแต็ก คุณอาจมีสตริงขนาดใหญ่อยู่ในนั้น และจากนั้น คุณจะล้นบัฟเฟอร์หาก recvfrom ได้รับข้อมูลจำนวนมาก

ฉันจะศึกษามันให้มากกว่านี้ถ้ามันไม่ได้ช่วย

person No One in Particular    schedule 21.10.2016

ปัญหาอยู่ในการโทรของคุณไปที่ recvfrom:

ret=recvfrom(sd1,(char *)bufptr,strlen(buffer),0,(struct sockaddr *)&clientaddr,&clen);

พารามิเตอร์ที่สามควรเป็นขนาดของบัฟเฟอร์อินพุต แต่คุณกำลังเรียก strlen บนบัฟเฟอร์แทน เนื่องจาก buffer ไม่ได้กำหนดค่าเริ่มต้น การเรียก strlen จึงเป็นการอ่านข้อมูลที่ยังไม่ได้กำหนดค่า ซึ่งอาจทำให้เกิด พฤติกรรมที่ไม่ได้กำหนด

นอกจากนี้ ยกเว้นกรณีที่ไคลเอ็นต์ส่งสตริงที่สิ้นสุดด้วยค่าว่าง (เช่น อักขระเครื่องพิมพ์บางตัวตามด้วยไบต์ว่าง) การเรียกไปยัง printf จะเรียกใช้พฤติกรรมที่ไม่ได้กำหนดไว้ด้วย เนื่องจากไบต์ใดๆ ที่ผ่านมาสิ่งที่อ่านจะถูกเตรียมใช้งานไม่ได้

ส่งผ่านขนาดบัฟเฟอร์ลบ 1 (เพื่อเว้นที่ว่างสำหรับไบต์ว่าง) แทนที่จะเรียก strlen และล้างบัฟเฟอร์ล่วงหน้า

memset(buffer, 0, sizeof(buffer));
ret=recvfrom(sd1,(char *)bufptr,sizeof(buffer)-1,0,(struct sockaddr *)&clientaddr,&clen);
person dbush    schedule 21.10.2016

ฉันคิดว่าคุณกำลังปิดซ็อกเก็ตที่อื่นในโปรแกรมของคุณ

Bad file descriptor อาจอ้างถึงตัวอธิบายไฟล์ที่ไม่ถูกต้อง หรือถูกปิดไว้ที่อื่นในโค้ดของคุณ หรือมีการใช้งานอยู่ที่อื่นแล้ว ฉันคิดว่าคุณต้องแก้ไขโค้ดของคุณสักหน่อยแล้วจัดการซ็อกเก็ตของคุณให้ดี

อาจเป็นไปได้ว่าซ็อกเก็ตของคุณถูกปิดที่ไหนสักแห่งโดยไม่ได้ตั้งใจหรือเสียหาย

คุณสามารถลองสร้างซ็อกเก็ตใหม่พร้อมกับหมายเลขพอร์ตอื่นได้

person Stubborn    schedule 21.10.2016
comment
ตกลงลองและยังคงประสบปัญหา จากนั้นแชร์รหัสลูกค้าของคุณด้วย - person Stubborn; 21.10.2016
comment
ใช่แล้ว... @ปากแข็ง - person Milan Shah; 22.10.2016