This is patch22 to PennMUSH 1.7.7. After applying this patch, you will have version 1.7.7p22 To apply this patch, save it to a file in your top-level MUSH directory, and do the following: patch -p1 < 1.7.7-patch22 ./Configure -d make install If you use GNU patch 2.2, you probably want the above to be 'patch -b -p1', not just 'patch -p1'. Unix (or cygwin) users need not worry about failed hunks in src/switchinc.c, hdrs/switches.h, hdrs/cmds.h, or hdrs/funs.h. These files are automatically rebuilt on compile. On the off chance they appear not to be, simply rm them and re-run make. Then @shutdown and restart your MUSH. - Alan/Javelin In this patch: Minor Changes: * When possible, sockets are now set SO_KEEPALIVE and TCP_KEEPIDLE. This may help prevent disconnections of idle players behind poorly designed NAT routers and the like, and make the use of the IDLE command unnecessary. Patch by Philip Mak. * Better failure messages for 'get blah's blah', especially when the container or contained object is ambiguous. Suggested by Philip Mak. Fixes: * Attempting to unset attribute flags actually set them. Report by Ambrosia@M*U*S*H. [SW] * Remove a warning in set.c. Report by Nymeria@M*U*S*H Prereq: 1.7.7p21 *** 1_7_7.665/Patchlevel Tue, 23 Sep 2003 11:50:22 -0500 dunemush (pennmush/5_Patchlevel 1.17.1.11.1.23 600) --- 1_7_7.672(w)/Patchlevel Tue, 30 Sep 2003 18:33:13 -0500 dunemush (pennmush/5_Patchlevel 1.17.1.11.1.24 600) *************** *** 1,2 **** Do not edit this file. It is maintained by the official PennMUSH patches. ! This is PennMUSH 1.7.7p21 --- 1,2 ---- Do not edit this file. It is maintained by the official PennMUSH patches. ! This is PennMUSH 1.7.7p22 *** 1_7_7.665/CHANGES.177 Mon, 29 Sep 2003 16:37:45 -0500 dunemush (pennmush/g/23_CHANGES 1.48.1.184 600) --- 1_7_7.672(w)/CHANGES.177 Tue, 30 Sep 2003 18:38:57 -0500 dunemush (pennmush/g/23_CHANGES 1.48.1.188 600) *************** *** 18,23 **** --- 18,39 ---- ========================================================================== + Version 1.7.7 patchlevel 22 September 30, 2003 + + Minor Changes: + * When possible, sockets are now set SO_KEEPALIVE and TCP_KEEPIDLE. + This may help prevent disconnections of idle players behind + poorly designed NAT routers and the like, and make the use of + the IDLE command unnecessary. Patch by Philip Mak. + * Better failure messages for 'get blah's blah', especially when + the container or contained object is ambiguous. Suggested by + Philip Mak. + Fixes: + * Attempting to unset attribute flags actually set them. + Report by Ambrosia@M*U*S*H. [SW] + * Remove a warning in set.c. Report by Nymeria@M*U*S*H + + Version 1.7.7 patchlevel 21 September 23, 2003 Major Changes: *** 1_7_7.665/config_h.SH Tue, 08 Apr 2003 22:03:08 -0500 dunemush (pennmush/b/17_config_h.S 1.17.1.2.1.1.1.8 660) --- 1_7_7.672(w)/config_h.SH Tue, 30 Sep 2003 17:54:40 -0500 dunemush (pennmush/b/17_config_h.S 1.17.1.2.1.1.1.9 660) *************** *** 786,791 **** --- 786,797 ---- */ #$i_netdb I_NETDB /**/ + /* I_NETINET_TCP: + * This symbol, if defined, indicates to the C program that it should + * include . + */ + #$i_nitcp I_NETINET_TCP /**/ + /* I_SETJMP: * This symbol, if defined, indicates to the C program that it can * include and have things work right. *************** *** 823,827 **** --- 829,845 ---- */ #$d_openssl HAS_OPENSSL /**/ + /* CAN_KEEPALIVE: + * This symbol if defined indicates to the C program that the SO_KEEPALIVE + * option of setsockopt() will work as advertised in the manual. + */ + /* CAN_KEEPIDLE: + * This symbol if defined indicates to the C program that the TCP_KEEPIDLE + * option of setsockopt() will work as advertised in the manual. + */ + #$d_keepalive CAN_KEEPALIVE /**/ + + #$d_keepidle CAN_KEEPIDLE /**/ + #endif !GROK!THIS! *** 1_7_7.665/src/set.c Mon, 29 Sep 2003 16:37:45 -0500 dunemush (pennmush/b/38_set.c 1.26.1.5.1.1.2.1.1.1.1.1.1.11.1.1.1.1.1.1.1.1.1.1.1.1.1.12 660) --- 1_7_7.672(w)/src/set.c Tue, 30 Sep 2003 18:50:55 -0500 dunemush (pennmush/b/38_set.c 1.26.1.5.1.1.2.1.1.1.1.1.1.11.1.1.1.1.1.1.1.1.1.1.1.1.1.15 660) *************** *** 458,464 **** /** Structure for af_helper() data. */ struct af_args { int f; /**< flag bits */ ! char const *flag; /**< flag name */ }; static int --- 458,465 ---- /** Structure for af_helper() data. */ struct af_args { int f; /**< flag bits */ ! int clear; /**< True to remove the flag */ ! char *flag; /**< flag name */ }; static int *************** *** 473,490 **** * There is one special case - the resetting of the SAFE flag. */ if (!(Can_Write_Attr(player, thing, AL_ATTR(atr)) || ! ((*af->flag == NOT_TOKEN) && (af->f == AF_SAFE) && Can_Write_Attr_Ignore_Safe(player, thing, AL_ATTR(atr))))) { notify_format(player, T("You cannot change that flag on %s/%s"), Name(thing), AL_NAME(atr)); return 0; } ! if (*af->flag == NOT_TOKEN) { AL_FLAGS(atr) &= ~af->f; if (!AreQuiet(player, thing)) notify_format(player, T("%s/%s - %s reset."), Name(thing), AL_NAME(atr), ! (af->flag + 1)); } else { AL_FLAGS(atr) |= af->f; if (!AreQuiet(player, thing)) --- 474,491 ---- * There is one special case - the resetting of the SAFE flag. */ if (!(Can_Write_Attr(player, thing, AL_ATTR(atr)) || ! (af->clear && (af->f == AF_SAFE) && Can_Write_Attr_Ignore_Safe(player, thing, AL_ATTR(atr))))) { notify_format(player, T("You cannot change that flag on %s/%s"), Name(thing), AL_NAME(atr)); return 0; } ! if (af->clear) { AL_FLAGS(atr) &= ~af->f; if (!AreQuiet(player, thing)) notify_format(player, T("%s/%s - %s reset."), Name(thing), AL_NAME(atr), ! af->flag); } else { AL_FLAGS(atr) |= af->f; if (!AreQuiet(player, thing)) *************** *** 530,538 **** notify(player, T("What flag do you want to set?")); return; } /* move past NOT token if there is one */ ! for (p = flag; *p && ((*p == NOT_TOKEN) || isspace((unsigned char) *p)); ! p++) ; if ((af.f = string_to_atrflag(player, p)) < 0) { notify(player, T("Unrecognized attribute flag.")); --- 531,543 ---- notify(player, T("What flag do you want to set?")); return; } + + af.clear = 0; + /* move past NOT token if there is one */ ! for (p = flag; *p && ((*p == NOT_TOKEN) || isspace((unsigned char) *p)); p++) ! if (*p == NOT_TOKEN) ! af.clear = !af.clear; if ((af.f = string_to_atrflag(player, p)) < 0) { notify(player, T("Unrecognized attribute flag.")); *************** *** 541,547 **** af.flag = mush_strdup(atrflag_to_string(af.f), "af_flag list"); if (!atr_iter_get(player, thing, atrname, 0, af_helper, &af)) notify(player, T("No attribute found to change.")); ! mush_free(af.flag, "af_flag list"); } --- 546,552 ---- af.flag = mush_strdup(atrflag_to_string(af.f), "af_flag list"); if (!atr_iter_get(player, thing, atrname, 0, af_helper, &af)) notify(player, T("No attribute found to change.")); ! mush_free((Malloc_t) af.flag, "af_flag list"); } *** 1_7_7.665/src/predicat.c Thu, 11 Sep 2003 15:26:04 -0500 dunemush (pennmush/b/44_predicat.c 1.1.1.34.1.1.1.3.1.4.2.28 660) --- 1_7_7.672(w)/src/predicat.c Tue, 30 Sep 2003 18:50:55 -0500 dunemush (pennmush/b/44_predicat.c 1.1.1.34.1.1.1.3.1.4.2.29 660) *************** *** 839,882 **** parse_que(player, "@notify me", cause); } ! /** Parse possessive matches. * This function parses strings of the form "Sam's bag" and attempts ! * to match "bag" in the contents of "Sam". It returns NOTHING if ! * there's no possessive 's in the string. * \param player the enactor/looker. ! * \param str a string to check for possessive matches. ! * \return matching dbref or NOTHING. */ dbref ! parse_match_possessive(dbref player, const char *str) { ! char *box; /* name of container */ char *obj; /* name of object */ - dbref loc; /* dbref of container */ - char name[BUFFER_LEN]; /* str would be destructively modified */ ! strcpy(name, str); ! box = name; /* check to see if we have an 's sequence */ ! if ((obj = strchr(name, '\'')) == NULL) return NOTHING; *obj++ = '\0'; /* terminate */ if ((*obj == '\0') || ((*obj != 's') && (*obj != 'S'))) return NOTHING; - /* skip over the 's' and whitespace */ do { obj++; } while (isspace((unsigned char) *obj)); /* we already have a terminating null, so we're okay to just do matches */ ! loc = match_result(player, box, NOTYPE, MAT_NEIGHBOR | MAT_POSSESSION); ! if (!GoodObject(loc)) ! return NOTHING; ! ! /* now we match on the contents */ ! return (match_result(loc, obj, NOTYPE, MAT_POSSESSION)); } --- 839,876 ---- parse_que(player, "@notify me", cause); } ! /** Parse possessive matches for the possessor. * This function parses strings of the form "Sam's bag" and attempts ! * to match "Sam". It returns NOTHING if ! * there's no possessive 's in the string. It destructively modifies ! * the string (terminating after the possessor name) and modifies the pointer ! * to the string to point at the name of the contained object. * \param player the enactor/looker. ! * \param str a pointer to a string to check for possessive matches. ! * \return matching dbref or NOTHING or AMBIGUOUS. */ dbref ! parse_match_possessor(dbref player, const char **str) { ! const char *box; /* name of container */ char *obj; /* name of object */ ! box = *str; /* check to see if we have an 's sequence */ ! if ((obj = strchr(box, '\'')) == NULL) return NOTHING; *obj++ = '\0'; /* terminate */ if ((*obj == '\0') || ((*obj != 's') && (*obj != 'S'))) return NOTHING; /* skip over the 's' and whitespace */ do { obj++; } while (isspace((unsigned char) *obj)); + *str = obj; /* we already have a terminating null, so we're okay to just do matches */ ! return match_result(player, box, NOTYPE, MAT_NEIGHBOR | MAT_POSSESSION); } *** 1_7_7.665/src/move.c Sat, 20 Sep 2003 12:59:32 -0500 dunemush (pennmush/b/51_move.c 1.1.1.18.1.5.1.13.1.3.1.9.1.1.1.1.1.2.1.1.1.1.1.22 660) --- 1_7_7.672(w)/src/move.c Tue, 30 Sep 2003 18:50:54 -0500 dunemush (pennmush/b/51_move.c 1.1.1.18.1.5.1.13.1.3.1.9.1.1.1.1.1.2.1.1.1.1.1.23 660) *************** *** 524,534 **** match_flags |= MAT_CONTROL; if (match_result(player, what, TYPE_THING, match_flags) == NOTHING) { if (POSSESSIVE_GET) { /* take care of possessive get (stealing) */ ! thing = parse_match_possessive(player, what); ! if (!GoodObject(thing)) { notify(player, T("I don't see that here.")); return; } /* to steal something, you have to be able to get it, and the * object must be ENTER_OK and not locked against you. --- 524,547 ---- match_flags |= MAT_CONTROL; if (match_result(player, what, TYPE_THING, match_flags) == NOTHING) { if (POSSESSIVE_GET) { + dbref box; + const char *boxname = what; /* take care of possessive get (stealing) */ ! box = parse_match_possessor(player, &what); ! if (box == NOTHING) { notify(player, T("I don't see that here.")); return; + } else if (box == AMBIGUOUS) { + notify_format(player, T("I can't tell which %s."), boxname); + return; + } + thing = match_result(box, what, NOTYPE, MAT_POSSESSION); + if (thing == NOTHING) { + notify(player, T("I don't see that here.")); + return; + } else if (thing == AMBIGUOUS) { + notify_format(player, T("I can't tell which %s."), what); + return; } /* to steal something, you have to be able to get it, and the * object must be ENTER_OK and not locked against you. *** 1_7_7.665/src/look.c Sat, 20 Sep 2003 12:59:32 -0500 dunemush (pennmush/c/4_look.c 1.21.1.2.1.9.1.1.1.1.1.17 660) --- 1_7_7.672(w)/src/look.c Tue, 30 Sep 2003 18:50:54 -0500 dunemush (pennmush/c/4_look.c 1.21.1.2.1.9.1.1.1.1.1.18 660) *************** *** 609,618 **** } /* look at a thing in location */ if ((thing = match_result(player, name, NOTYPE, MAT_NEARBY)) == NOTHING) { ! thing = parse_match_possessive(player, name); ! if (!GoodObject(thing)) { notify(player, T("I don't see that here.")); return; } if (Opaque(Location(thing)) && (!See_All(player) && --- 609,631 ---- } /* look at a thing in location */ if ((thing = match_result(player, name, NOTYPE, MAT_NEARBY)) == NOTHING) { ! dbref box; ! const char *boxname = name; ! box = parse_match_possessor(player, &name); ! if (box == NOTHING) { notify(player, T("I don't see that here.")); return; + } else if (box == AMBIGUOUS) { + notify_format(player, T("I can't tell which %s."), boxname); + return; + } + thing = match_result(box, name, NOTYPE, MAT_POSSESSION); + if (thing == NOTHING) { + notify(player, T("I don't see that here.")); + return; + } else if (thing == AMBIGUOUS) { + notify_format(player, T("I can't tell which %s."), name); + return; } if (Opaque(Location(thing)) && (!See_All(player) && *** 1_7_7.665/src/bsd.c Sun, 14 Sep 2003 09:18:01 -0500 dunemush (pennmush/c/38_bsd.c 1.58.1.11.1.2.1.5.1.7.1.14.1.13.1.9.1.4.1.2.1.12.1.1.1.1.1.2.1.1.1.13.1.1.1.1.1.1.1.1.1.1.1.3.1.1.1.1.1.1.1.1.1.1.1.1.1.1.1.3.1.8.2.1.1.1.1.1.1.1.1.2.1.1.1.1.1.1.1.1.1.1.1.1.1.2 660) --- 1_7_7.672(w)/src/bsd.c Tue, 30 Sep 2003 18:50:52 -0500 dunemush (pennmush/c/38_bsd.c 1.58.1.11.1.2.1.5.1.7.1.14.1.13.1.9.1.4.1.2.1.12.1.1.1.1.1.2.1.1.1.13.1.1.1.1.1.1.1.1.1.1.1.3.1.1.1.1.1.1.1.1.1.1.1.1.1.1.1.3.1.8.2.1.1.1.1.1.1.1.1.2.1.1.1.1.1.1.1.1.1.1.1.1.1.3 660) *************** *** 134,139 **** --- 134,140 ---- #endif #endif + /* BSD 4.2 and maybe some others need these defined */ #ifndef FD_ZERO /** An fd_set is 4 bytes */ *************** *** 1320,1325 **** --- 1321,1327 ---- } do_log(LT_CONN, 0, 0, T("[%d/%s/%s] Connection opened."), newsock, tbuf1, tbuf2); + set_keepalive(newsock); return initializesock(newsock, tbuf1, tbuf2, use_ssl); } #endif *************** *** 2097,2102 **** --- 2099,2105 ---- } do_log(LT_CONN, 0, 0, T("[%d/%s/%s] Connection opened."), fd, bp ? bp : "", buf); + set_keepalive(fd); (void) initializesock(fd, bp ? bp : buf, buf, (atoi(bp2) == SSLPORT)); } } *** 1_7_7.665/hdrs/version.h Tue, 23 Sep 2003 11:50:22 -0500 dunemush (pennmush/c/47_version.h 1.32.1.2.1.7.1.9.1.1.1.17.1.25 660) --- 1_7_7.672(w)/hdrs/version.h Tue, 30 Sep 2003 18:50:56 -0500 dunemush (pennmush/c/47_version.h 1.32.1.2.1.7.1.9.1.1.1.17.1.26 660) *************** *** 1,3 **** ! #define VERSION "PennMUSH version 1.7.7 patchlevel 21 [09/23/2003]" ! #define SHORTVN "PennMUSH 1.7.7p21" ! #define NUMVERSION 001007007021 --- 1,3 ---- ! #define VERSION "PennMUSH version 1.7.7 patchlevel 22 [09/30/2003]" ! #define SHORTVN "PennMUSH 1.7.7p22" ! #define NUMVERSION 001007007022 *** 1_7_7.665/hdrs/externs.h Thu, 11 Sep 2003 15:26:04 -0500 dunemush (pennmush/d/16_externs.h 1.1.1.53.1.2.1.8.2.1.1.2.1.1.1.1.1.2.1.6.1.3.1.4.3.1.1.1.1.18.1.1 660) --- 1_7_7.672(w)/hdrs/externs.h Tue, 30 Sep 2003 18:50:56 -0500 dunemush (pennmush/d/16_externs.h 1.1.1.53.1.2.1.8.2.1.1.2.1.1.1.1.1.2.1.6.1.3.1.4.3.1.1.1.1.18.1.2 660) *************** *** 272,278 **** extern int ok_command_name(const char *name); extern int ok_player_name(const char *name, dbref player); extern int ok_password(const char *password); ! extern dbref parse_match_possessive(dbref player, const char *str); extern void page_return(dbref player, dbref target, const char *type, const char *message, const char *def); extern char *grep_util(dbref player, dbref thing, char *pattern, --- 272,278 ---- extern int ok_command_name(const char *name); extern int ok_player_name(const char *name, dbref player); extern int ok_password(const char *password); ! extern dbref parse_match_possessor(dbref player, const char **str); extern void page_return(dbref player, dbref target, const char *type, const char *message, const char *def); extern char *grep_util(dbref player, dbref thing, char *pattern, *** 1_7_7.665/hdrs/copyrite.h Tue, 08 Oct 2002 11:03:38 -0500 dunemush (pennmush/d/19_copyrite.h 1.3 660) --- 1_7_7.672(w)/hdrs/copyrite.h Tue, 30 Sep 2003 18:50:56 -0500 dunemush (pennmush/d/19_copyrite.h 1.4 660) *************** *** 41,49 **** * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. * * The portions derived from TinyMUSH 2.2 are used under the Artistic ! * License. The Artistic License is also the license under which you ! * are granted permission to copy and modify PennMUSH: * * The Artistic License * --- 41,61 ---- * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. * + * Although not necessary given the above copyright, the TinyMUSH 2.0 + * developers, Joseph Traub and Glenn Crocker, confirmed in email to + * Alan Schwartz in 2002 that they were willing to have any of their + * code present in PennMUSH redistributed under the Artistic License. + * * The portions derived from TinyMUSH 2.2 are used under the Artistic ! * License. Jean Marie Diaz, Lydia Leong, and Devin Hooker, the ! * TinyMUSH 2.2 copyright holders, explicitly agreed to relicense ! * their source code under the Artistic License in 2002, and TinyMUSH 2.2.5 ! * was released under this license; Alan Schwartz has confirmatory email ! * from them authorizing the redistribution of any portions of TinyMUSH 2.2 ! * that may be present in PennMUSH under the Artistic License. ! * ! * The Artistic License is also the license under which you ! * are granted permission to copy, modify, and redistribute PennMUSH: * * The Artistic License * *** 1_7_7.665/COPYRITE Tue, 08 Oct 2002 11:03:38 -0500 dunemush (pennmush/d/29_COPYRITE 1.5 600) --- 1_7_7.672(w)/COPYRITE Tue, 30 Sep 2003 18:31:05 -0500 dunemush (pennmush/d/29_COPYRITE 1.6 600) *************** *** 41,49 **** * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. * * The portions derived from TinyMUSH 2.2 are used under the Artistic ! * License. The Artistic License is also the license under which you ! * are granted permission to copy and modify PennMUSH: * * The Artistic License * --- 41,61 ---- * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. * + * Although not necessary given the above copyright, the TinyMUSH 2.0 + * developers, Joseph Traub and Glenn Crocker, confirmed in email to + * Alan Schwartz in 2002 that they were willing to have any of their + * code present in PennMUSH redistributed under the Artistic License. + * * The portions derived from TinyMUSH 2.2 are used under the Artistic ! * License. Jean Marie Diaz, Lydia Leong, and Devin Hooker, the ! * TinyMUSH 2.2 copyright holders, explicitly agreed to relicense ! * their source code under the Artistic License in 2002, and TinyMUSH 2.2.5 ! * was released under this license; Alan Schwartz has confirmatory email ! * from them authorizing the redistribution of any portions of TinyMUSH 2.2 ! * that may be present in PennMUSH under the Artistic License. ! * ! * The Artistic License is also the license under which you ! * are granted permission to copy, modify, and redistribute PennMUSH: * * The Artistic License * *** 1_7_7.665/Configure Wed, 20 Aug 2003 15:48:01 -0500 dunemush (pennmush/d/32_Configure 1.21.1.4.1.1.1.1.1.1.1.7.1.3 710) --- 1_7_7.672(w)/Configure Tue, 30 Sep 2003 17:54:40 -0500 dunemush (pennmush/d/32_Configure 1.21.1.4.1.1.1.1.1.1.1.7.1.4 710) *************** *** 366,371 **** --- 366,372 ---- i_netdb='' i_niin='' i_sysin='' + i_nitcp='' i_setjmp='' i_stddef='' i_stdlib='' *************** *** 439,444 **** --- 440,447 ---- sh='' sizetype='' so='' + d_keepalive='' + d_keepidle='' sharpbang='' shsharp='' spitshell='' *************** *** 4520,4525 **** --- 4523,4660 ---- set setitimer d_itimer eval $inlibc + socketlib='' + sockethdr='' + : see whether socket exists + echo " " + $echo $n "Hmm... $c" >&4 + if set socket val -f d_socket; eval $csym; $val; then + echo "Looks like you have Berkeley networking support." >&4 + d_socket="$define" + if set setsockopt val -f; eval $csym; $val; then + d_oldsock="$undef" + else + echo "...but it uses the old 4.1c interface, rather than 4.2" >&4 + d_oldsock="$define" + fi + else + if $contains socklib libc.list >/dev/null 2>&1; then + echo "Looks like you have Berkeley networking support." >&4 + d_socket="$define" + : we will have to assume that it supports the 4.2 BSD interface + d_oldsock="$undef" + else + echo "You don't have Berkeley networking in libc$_a..." >&4 + if test -f /usr/lib/libnet$_a; then + ( (nm $nm_opt /usr/lib/libnet$_a | eval $nm_extract) || \ + ar t /usr/lib/libnet$_a) 2>/dev/null >> libc.list + if $contains socket libc.list >/dev/null 2>&1; then + echo "...but the Wollongong group seems to have hacked it in." >&4 + socketlib="-lnet" + sockethdr="-I/usr/netinclude" + d_socket="$define" + if $contains setsockopt libc.list >/dev/null 2>&1; then + d_oldsock="$undef" + else + echo "...using the old 4.1c interface, rather than 4.2" >&4 + d_oldsock="$define" + fi + else + echo "or even in libnet$_a, which is peculiar." >&4 + d_socket="$undef" + d_oldsock="$undef" + fi + else + echo "or anywhere else I see." >&4 + d_socket="$undef" + d_oldsock="$undef" + fi + fi + fi + + : see if socketpair exists + set socketpair d_sockpair + eval $inlibc + + : see if this is a netinet/tcp.h system + set netinet/tcp.h i_nitcp + eval $inhdr + + : see if setsockopt with SO_KEEPALIVE works as advertised + echo " " + case "$d_oldsock" in + "$undef") + echo "OK, let's see if SO_KEEPALIVE works as advertised..." >&4 + $cat > socket.c < + #include + #include + #$i_nitcp I_NETINET_TCP + #ifdef I_NETINET_TCP + #include + #endif + #include + + main() + { + int s = socket(AF_INET, SOCK_STREAM, 0); + int val = 1; + if (s == -1) + exit(1); + if (-1 == setsockopt(s, SOL_SOCKET, SO_KEEPALIVE, &val, sizeof(val))) + exit(2); + #ifdef I_NETINET_TCP + val = 1; + if (-1 == setsockopt(s, IPPROTO_TCP, TCP_KEEPIDLE, &val, sizeof(val))) + exit(3); + #endif + exit(0); + } + EOP + if $cc $ccflags $sockethdr socket.c -o socket $libs \ + $socketlib >/dev/null 2>&1; then + ./socket >/dev/null 2>&1 + case $? in + 0) echo "Yes, it does!" + val="$define" + val2="$i_nitcp" + ;; + 1) $cat <&4 - if set socket val -f d_socket; eval $csym; $val; then - echo "Looks like you have Berkeley networking support." >&4 - d_socket="$define" - if set setsockopt val -f; eval $csym; $val; then - d_oldsock="$undef" - else - echo "...but it uses the old 4.1c interface, rather than 4.2" >&4 - d_oldsock="$define" - fi - else - if $contains socklib libc.list >/dev/null 2>&1; then - echo "Looks like you have Berkeley networking support." >&4 - d_socket="$define" - : we will have to assume that it supports the 4.2 BSD interface - d_oldsock="$undef" - else - echo "You don't have Berkeley networking in libc$_a..." >&4 - if test -f /usr/lib/libnet$_a; then - ( (nm $nm_opt /usr/lib/libnet$_a | eval $nm_extract) || \ - ar t /usr/lib/libnet$_a) 2>/dev/null >> libc.list - if $contains socket libc.list >/dev/null 2>&1; then - echo "...but the Wollongong group seems to have hacked it in." >&4 - socketlib="-lnet" - sockethdr="-I/usr/netinclude" - d_socket="$define" - if $contains setsockopt libc.list >/dev/null 2>&1; then - d_oldsock="$undef" - else - echo "...using the old 4.1c interface, rather than 4.2" >&4 - d_oldsock="$define" - fi - else - echo "or even in libnet$_a, which is peculiar." >&4 - d_socket="$undef" - d_oldsock="$undef" - fi - else - echo "or anywhere else I see." >&4 - d_socket="$undef" - d_oldsock="$undef" - fi - fi - fi - - : see if socketpair exists - set socketpair d_sockpair - eval $inlibc - : see if we have socklen_t. echo " " $cat >d_socklen.c < + #endif + #ifdef I_ARPA_INET #include #endif *************** *** 357,362 **** --- 361,393 ---- #endif /* !macintosh */ } + + + /* Enable TCP keepalive on the given socket if we can */ + void + set_keepalive(int s) + { + #ifdef CAN_KEEPALIVE + int keepalive = 1; + #ifdef CAN_KEEPIDLE + int keepidle = 900; + #endif + + /* enable TCP keepalive */ + if (setsockopt(s, SOL_SOCKET, SO_KEEPALIVE, + (void *) &keepalive, sizeof(keepalive)) == -1) + fprintf(stderr, "[%d] could not set SO_KEEPALIVE: errno %d", s, errno); + #ifdef CAN_KEEPIDLE + if (setsockopt(s, IPPROTO_TCP, TCP_KEEPIDLE, + (void *) &keepidle, sizeof(keepidle)) == -1) + fprintf(stderr, "[%d] could not set TCP_KEEPALIVE: errno %d", s, errno); + #endif + #endif + return; + } + + + /** Connect a socket, possibly making it nonblocking first. * From UNP, with changes. If nsec > 0, we set the socket * nonblocking and connect with timeout. The socket is STILL *** 1_7_7.665/game/txt/hlp/pennvOLD.hlp Sun, 14 Sep 2003 09:18:01 -0500 dunemush (pennmush/g/30_pennvOLD.h 1.1.1.1.1.1.1.1.1.1.1.1.1.2 660) --- 1_7_7.672(w)/game/txt/hlp/pennvOLD.hlp Tue, 30 Sep 2003 18:50:57 -0500 dunemush (pennmush/g/30_pennvOLD.h 1.1.1.1.1.1.1.1.1.1.1.1.1.3 660) *************** *** 4418,4424 **** type 'help p'. For example, 'help 1.7.2p3' 1.7.7: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, ! 19, 20, 21 1.7.6: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14 1.7.5: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12 1.7.4: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, --- 4418,4424 ---- type 'help p'. For example, 'help 1.7.2p3' 1.7.7: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, ! 19, 20, 21, 22 1.7.6: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14 1.7.5: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12 1.7.4: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, *** 1_7_7.665/game/txt/hlp/pennv177.hlp Mon, 29 Sep 2003 16:37:45 -0500 dunemush (pennmush/g/34_pennv177.h 1.153 660) --- 1_7_7.672(w)/game/txt/hlp/pennv177.hlp Tue, 30 Sep 2003 18:50:56 -0500 dunemush (pennmush/g/34_pennv177.h 1.157 660) *************** *** 1,4 **** ! & 1.7.7p21 & changes This is a list of changes in this patchlevel which are probably of interest to players. More information about new commands and functions --- 1,4 ---- ! & 1.7.7p22 & changes This is a list of changes in this patchlevel which are probably of interest to players. More information about new commands and functions *************** *** 11,16 **** --- 11,33 ---- A list of the patchlevels associated with each release can be read in 'help patchlevels'. + Version 1.7.7 patchlevel 22 September 30, 2003 + + Minor Changes: + * When possible, sockets are now set SO_KEEPALIVE and TCP_KEEPIDLE. + This may help prevent disconnections of idle players behind + poorly designed NAT routers and the like, and make the use of + the IDLE command unnecessary. Patch by Philip Mak. + * Better failure messages for 'get blah's blah', especially when + the container or contained object is ambiguous. Suggested by + Philip Mak. + Fixes: + * Attempting to unset attribute flags actually set them. + Report by Ambrosia@M*U*S*H. [SW] + * Remove a warning in set.c. Report by Nymeria@M*U*S*H + + + & 1.7.7p21 Version 1.7.7 patchlevel 21 September 23, 2003 Major Changes: