免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 6090 | 回复: 13
打印 上一主题 下一主题

多线程编程出现Segmentation fault,请高手帮忙分析 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2008-11-08 14:11 |只看该作者 |倒序浏览
5可用积分
pid  3287] write(1252, "<html><head>\n\n  \n    \n    \n    \n"..., 131072 <unfinished ...>
[pid  3286] <... epoll_wait resumed> {{EPOLLIN, {u32=186946376, u64=17117145668555592}}}, 40000, -1) = 1
[pid  3286] epoll_wait(11,  <unfinished ...>
[pid  3287] <... write resumed> )       = 13140
[pid  3287] write(1252, "llCatPopoverDiv_OuterX\"><span id"..., 117932) = -1 EAGAIN (Resource temporarily unavailable)
[pid  3287] select(1253, NULL, [1024 1025 1154 1155 1156 1157 1160 1164 1165 1167 1168 1169 1170 1171 1173 1174 1175 1177 1178 1180 1181 1183 1187 1196 1197 1200 1201 1202 1203 1205 1213 1215 1219 1223 1224 1226 1229 1231 1232 1235 1236 1237 1238 1241 1243 1251 1252], NULL, {3, 0}) = 46 (out [1024 1025 1154 1155 1156 1157 1160 1164 1165 1167 1168 1169 1170 1171 1173 1174 1175 1177 1178 1180 1181 1183 1187 1196 1197 1200 1201 1202 1203 1205 1213 1215 1219 1223 1224 1226 1229 1231 1232 1235 1236 1237 1238 1241 1243 1251], left {3, 0})
[pid  3287] --- SIGSEGV (Segmentation fault) @ 0 (0) ---

反复看过代码,select之后是printf函数,不可能出现段错误.而且并不是程序一运行到这边就出错.是运行一段时间后出现(几分钟不等).

还有一个疑问是,select的maxfd是否可以大于1024, select之前我已经FD_ZERO(&fdSet);  FD_SET(1252, &fdSet);为什么select的系统调用打印出那么多FD出来呀: [1024 1025 1154 1155 1156 1157 1160 ...

论坛徽章:
3
戌狗
日期:2014-09-10 17:07:162015年辞旧岁徽章
日期:2015-03-03 16:54:15wusuopu
日期:2016-06-17 17:43:45
2 [报告]
发表于 2008-11-08 14:16 |只看该作者
select的maxfd是否可以大于1024,

FD_SETSIZE系统有个最大值限制。默认是1024,修改需重新编译内核

[ 本帖最后由 ynchnluiti 于 2008-11-8 14:20 编辑 ]

论坛徽章:
0
3 [报告]
发表于 2008-11-08 14:26 |只看该作者
原帖由 ynchnluiti 于 2008-11-8 14:16 发表

FD_SETSIZE系统有个最大值限制。默认是1024,修改需重新编译内核


FD_SETSIZE, 好象是select一次可处理的fd数量吧.我现在select只侦听一个FD,只是这个FD的值大于1024而已

论坛徽章:
3
戌狗
日期:2014-09-10 17:07:162015年辞旧岁徽章
日期:2015-03-03 16:54:15wusuopu
日期:2016-06-17 17:43:45
4 [报告]
发表于 2008-11-08 14:29 |只看该作者
原帖由 mackon_jong 于 2008-11-8 14:26 发表


FD_SETSIZE, 好象是select一次可处理的fd数量吧.我现在select只侦听一个FD,只是这个FD的值大于1024而已


man select
An fd_set is a fixed size buffer.  Executing FD_CLR() or FD_SET() with a value of fd that is negative or is  equal to  or  larger  than  FD_SETSIZE will result in undefined behavior. Moreover, POSIX requires fd to be a valid file
descriptor.

[ 本帖最后由 ynchnluiti 于 2008-11-8 14:42 编辑 ]

论坛徽章:
0
5 [报告]
发表于 2008-11-08 15:25 |只看该作者
原帖由 ynchnluiti 于 2008-11-8 14:29 发表


man select

有什么好的解决办法,用epoll

论坛徽章:
3
戌狗
日期:2014-09-10 17:07:162015年辞旧岁徽章
日期:2015-03-03 16:54:15wusuopu
日期:2016-06-17 17:43:45
6 [报告]
发表于 2008-11-08 15:36 |只看该作者
LZ 是select 和 epoll混用? 应该只选择其一

论坛徽章:
0
7 [报告]
发表于 2008-11-08 15:44 |只看该作者
我觉得epoll没啥不好,比select好很多,也很易用。除非开发环境不是2.6的内核

[ 本帖最后由 waternie 于 2008-11-8 15:45 编辑 ]

论坛徽章:
0
8 [报告]
发表于 2008-11-08 16:12 |只看该作者
改成epoll还是出错
[pid  3340] epoll_create(65535)         = 1230
[pid  3340] epoll_ctl(1230, EPOLL_CTL_ADD, 1252, {EPOLLOUT, {u32=165158888, u64=15763973250490344}}) = 0
[pid  3340] epoll_wait(1230, {{EPOLLOUT, {u32=165158888, u64=15763973250490344}}}, 1, 3) = 1
[pid  3340] close(1230)                 = 0
[pid  3340] write(1, "yhl test before checkout(3) <--B"..., 92yhl test before checkout(3) <--BaseSocket.cpp:437yhl test epoll_wait=1 <--BaseSocket.cpp:77
) = 92
[pid  3340] write(1, "yhl test selectEINTR1=1\n", 24yhl test selectEINTR1=1
) = 24
[pid  3340] --- SIGSEGV (Segmentation fault) @ 0 (0) ---

我把我的函数调用贴上来.按程序流程, [pid  3340] write(1, "yhl test selectEINTR1=1\n", 24yhl test selectEINTR1=1后,应该是printf("yhl test after checkout(%d)=%d <--%s:%d",  timeout, ret, __FILE__, __LINE__), 但却出现段错误了,会不会别的线程访问指针越界,修改了我这个线程的堆栈数据.

int selectEINTR1(int fd, int event, int timeout)
{
    int epfd;
    struct epoll_event ev;
    struct epoll_event events[1];
    int rc;

    ev.events = event;//ev.events = event | EPOLLET | EPOLLONESHOT;

    epfd = epoll_create (65535);
    if (epfd == -1){
        printf("create epoll fail<--%s:%d\n", __FILE__, __LINE__);
        return 0;
    }

    if (epoll_ctl (epfd, EPOLL_CTL_ADD, fd, &ev) != 0){
        if (epoll_ctl (epfd, EPOLL_CTL_MOD, fd, &ev) != 0){
            printf("epoll_ctl fail<--%s:%d\n", __FILE__, __LINE__);
            return 0;
        }
    }

    rc = epoll_wait (epfd, events, 1, timeout*1000);
    close(epfd);
    printf("yhl test epoll_wait=%d <--%s:%d\n", rc, __FILE__, __LINE__);

    return rc;
}

int BaseSocket::readyForOutput(int timeout)
{
    int ret = 0;

    //ret = selectEINTR(sck + 1, NULL, &fdSet, NULL, &t);
    ret = selectEINTR1(sck, EPOLLOUT, timeout);
    printf("yhl test selectEINTR1=%d\n <--%s:%d", ret, __FILE__, __LINE__);

    return ret;
}
bool BaseSocket::writeToSocket(char *buff, int len, int timeout, bool check_first) throw(exception)
{
    int actuallysent = 0;
    int sent;
    bool firstflag = true;
    int errcount = 0;
    int ret = 0;

    while (actuallysent < len) {
        sent = write(sck, buff + actuallysent, len - actuallysent);
        if (sent < 0) {
            if (errno == EAGAIN && errcount < 3){
                printf("yhl test before checkout(%d) <--%s:%d",  timeout,  __FILE__, __LINE__);
                ret = readyForOutput(timeout);
                printf("yhl test after checkout(%d)=%d <--%s:%d",  timeout, ret, __FILE__, __LINE__);
                if (ret < 0)
                    return false;
                else if (ret == 0)
                    errcount++;
                else
                    errcount = 0;

                continue;
            }
            return false;
        }
        else if (sent == 0) {
            errcount = 0;
            return false;  // other end is closed
        }

        actuallysent += sent;
    }

    //do_log(LOG_DEBUG, "yhl test send actuallysent:%d <--%s:%d", actuallysent, __FILE__, __LINE__);
    return true;
}

论坛徽章:
0
9 [报告]
发表于 2008-11-08 16:38 |只看该作者
各位大侠,帮忙分析下可能是什么原因引起的.谢谢!!!

论坛徽章:
3
戌狗
日期:2014-09-10 17:07:162015年辞旧岁徽章
日期:2015-03-03 16:54:15wusuopu
日期:2016-06-17 17:43:45
10 [报告]
发表于 2008-11-08 17:26 |只看该作者
sent = write(sck, buff + actuallysent, len - actuallysent);
多线程同时运行,buff的内容能保证吧?
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP