X-Git-Url: https://git.ozlabs.org/?a=blobdiff_plain;f=pppd%2Fsys-linux.c;h=4c04e7e5c2d005bf0a37994b1dbc21cda4e4b488;hb=5c62101f3ba79a98b2651cfa4704a0ef1ceecdfb;hp=8d6eee93550622d5cbe0b9803fe714c11d65b713;hpb=2883dd07101bf851e2ea368f0c04c91aea85cff2;p=ppp.git diff --git a/pppd/sys-linux.c b/pppd/sys-linux.c index 8d6eee9..4c04e7e 100644 --- a/pppd/sys-linux.c +++ b/pppd/sys-linux.c @@ -697,11 +697,11 @@ static int make_ppp_unit(void) if (x == 0 && req_ifname[0] != '\0') { struct ifreq ifr; - char t[MAXIFNAMELEN]; + char t[IFNAMSIZ]; memset(&ifr, 0, sizeof(struct ifreq)); slprintf(t, sizeof(t), "%s%d", PPP_DRV_NAME, ifunit); - strlcpy(ifr.ifr_name, t, IF_NAMESIZE); - strlcpy(ifr.ifr_newname, req_ifname, IF_NAMESIZE); + strlcpy(ifr.ifr_name, t, IFNAMSIZ); + strlcpy(ifr.ifr_newname, req_ifname, IFNAMSIZ); x = ioctl(sock_fd, SIOCSIFNAME, &ifr); if (x < 0) error("Couldn't rename interface %s to %s: %m", t, req_ifname); @@ -3013,7 +3013,14 @@ static int sif6addr_rtnetlink(unsigned int iface, eui64_t our_eui64, eui64_t his /* error == 0 indicates success, negative value is errno code */ if (nlresp.nlerr.error != 0) { - error("sif6addr_rtnetlink: %s (line %d)", strerror(-nlresp.nlerr.error), __LINE__); + /* + * Linux kernel versions prior 3.11 do not support setting IPv6 peer + * addresses and error response is expected. On older kernel versions + * do not show this error message. On error pppd tries to fallback to + * the old IOCTL method. + */ + if (kernel_version >= KVERSION(3,11,0)) + error("sif6addr_rtnetlink: %s (line %d)", strerror(-nlresp.nlerr.error), __LINE__); return 0; } @@ -3029,6 +3036,7 @@ int sif6addr (int unit, eui64_t our_eui64, eui64_t his_eui64) struct in6_ifreq ifr6; struct ifreq ifr; struct in6_rtmsg rt6; + int ret; if (sock6_fd < 0) { errno = -sock6_fd; @@ -3044,8 +3052,16 @@ int sif6addr (int unit, eui64_t our_eui64, eui64_t his_eui64) if (kernel_version >= KVERSION(2,1,16)) { /* Set both local address and remote peer address (with route for it) via rtnetlink */ - return sif6addr_rtnetlink(ifr.ifr_ifindex, our_eui64, his_eui64); + ret = sif6addr_rtnetlink(ifr.ifr_ifindex, our_eui64, his_eui64); } else { + ret = 0; + } + + /* + * Linux kernel versions prior 3.11 do not support setting IPv6 peer address + * via rtnetlink. So if sif6addr_rtnetlink() fails then try old IOCTL method. + */ + if (!ret) { /* Local interface */ memset(&ifr6, 0, sizeof(ifr6)); IN6_LLADDR_FROM_EUI64(ifr6.ifr6_addr, our_eui64); @@ -3127,7 +3143,7 @@ int cif6addr (int unit, eui64_t our_eui64, eui64_t his_eui64) int get_pty(int *master_fdp, int *slave_fdp, char *slave_name, int uid) { - int i, mfd, sfd = -1; + int i, mfd, ret, sfd = -1; char pty_name[16]; struct termios tios; @@ -3165,8 +3181,14 @@ get_pty(int *master_fdp, int *slave_fdp, char *slave_name, int uid) pty_name[5] = 't'; sfd = open(pty_name, O_RDWR | O_NOCTTY, 0); if (sfd >= 0) { - fchown(sfd, uid, -1); - fchmod(sfd, S_IRUSR | S_IWUSR); + ret = fchown(sfd, uid, -1); + if (ret != 0) { + warn("Couldn't change ownership of %s, %m", pty_name); + } + ret = fchmod(sfd, S_IRUSR | S_IWUSR); + if (ret != 0) { + warn("Couldn't change permissions of %s, %m", pty_name); + } break; } close(mfd);