Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit f0483631 authored by Mike J. Chen's avatar Mike J. Chen Committed by Android (Google) Code Review
Browse files

Merge changes I255cca69,Ice9ec7f0,I4e97ac98

* changes:
  Workaround Motorola ril.so incompatiblity with Netlink changes
  Cleanup NetlinkListener and NetlinkEvent
  Revert "Revert "Add NETLINK_ROUTE processing to the netlink client code, so that Ethernet""
parents 7b023b29 2a56688d
Loading
Loading
Loading
Loading
+9 −1
Original line number Original line Diff line number Diff line
@@ -16,6 +16,8 @@
#ifndef _NETLINKEVENT_H
#ifndef _NETLINKEVENT_H
#define _NETLINKEVENT_H
#define _NETLINKEVENT_H


#include <sysutils/NetlinkListener.h>

#define NL_PARAMS_MAX 32
#define NL_PARAMS_MAX 32


class NetlinkEvent {
class NetlinkEvent {
@@ -30,17 +32,23 @@ public:
    const static int NlActionAdd;
    const static int NlActionAdd;
    const static int NlActionRemove;
    const static int NlActionRemove;
    const static int NlActionChange;
    const static int NlActionChange;
    const static int NlActionLinkDown;
    const static int NlActionLinkUp;


    NetlinkEvent();
    NetlinkEvent();
    virtual ~NetlinkEvent();
    virtual ~NetlinkEvent();


    bool decode(char *buffer, int size);
    bool decode(char *buffer, int size, int format = NetlinkListener::NETLINK_FORMAT_ASCII);
    const char *findParam(const char *paramName);
    const char *findParam(const char *paramName);


    const char *getSubsystem() { return mSubsystem; }
    const char *getSubsystem() { return mSubsystem; }
    int getAction() { return mAction; }
    int getAction() { return mAction; }


    void dump();
    void dump();

 protected:
    bool parseBinaryNetlinkMessage(char *buffer, int size);
    bool parseAsciiNetlinkMessage(char *buffer, int size);
};
};


#endif
#endif
+14 −0
Original line number Original line Diff line number Diff line
@@ -22,13 +22,27 @@ class NetlinkEvent;


class NetlinkListener : public SocketListener {
class NetlinkListener : public SocketListener {
    char mBuffer[64 * 1024];
    char mBuffer[64 * 1024];
    int mFormat;


public:
public:
    static const int NETLINK_FORMAT_ASCII = 0;
    static const int NETLINK_FORMAT_BINARY = 1;

#if 1
    /* temporary version until we can get Motorola to update their
     * ril.so.  Their prebuilt ril.so is using this private class
     * so changing the NetlinkListener() constructor breaks their ril.
     */
    NetlinkListener(int socket);
    NetlinkListener(int socket);
    NetlinkListener(int socket, int format);
#else
    NetlinkListener(int socket, int format = NETLINK_FORMAT_ASCII);
#endif
    virtual ~NetlinkListener() {}
    virtual ~NetlinkListener() {}


protected:
protected:
    virtual bool onDataAvailable(SocketClient *cli);
    virtual bool onDataAvailable(SocketClient *cli);
    virtual void onEvent(NetlinkEvent *evt) = 0;
    virtual void onEvent(NetlinkEvent *evt) = 0;
};
};

#endif
#endif
+65 −1
Original line number Original line Diff line number Diff line
@@ -21,10 +21,17 @@


#include <sysutils/NetlinkEvent.h>
#include <sysutils/NetlinkEvent.h>


#include <sys/types.h>
#include <sys/socket.h>
#include <linux/rtnetlink.h>
#include <linux/if.h>

const int NetlinkEvent::NlActionUnknown = 0;
const int NetlinkEvent::NlActionUnknown = 0;
const int NetlinkEvent::NlActionAdd = 1;
const int NetlinkEvent::NlActionAdd = 1;
const int NetlinkEvent::NlActionRemove = 2;
const int NetlinkEvent::NlActionRemove = 2;
const int NetlinkEvent::NlActionChange = 3;
const int NetlinkEvent::NlActionChange = 3;
const int NetlinkEvent::NlActionLinkUp = 4;
const int NetlinkEvent::NlActionLinkDown = 5;


NetlinkEvent::NetlinkEvent() {
NetlinkEvent::NetlinkEvent() {
    mAction = NlActionUnknown;
    mAction = NlActionUnknown;
@@ -56,6 +63,51 @@ void NetlinkEvent::dump() {
    }
    }
}
}


/*
 * Parse an binary message from a NETLINK_ROUTE netlink socket.
 */
bool NetlinkEvent::parseBinaryNetlinkMessage(char *buffer, int size) {
    size_t sz = size;
    const struct nlmsghdr *nh = (struct nlmsghdr *) buffer;

    while (NLMSG_OK(nh, sz) && (nh->nlmsg_type != NLMSG_DONE)) {
        if (nh->nlmsg_type == RTM_NEWLINK) {
            int len = nh->nlmsg_len - sizeof(*nh);
            struct ifinfomsg *ifi;

            if (sizeof(*ifi) <= (size_t) len) {
                ifi = (ifinfomsg *)NLMSG_DATA(nh);

                if ((ifi->ifi_flags & IFF_LOOPBACK) == 0) {
                    struct rtattr *rta = (struct rtattr *)
                      ((char *) ifi + NLMSG_ALIGN(sizeof(*ifi)));
                    len = NLMSG_PAYLOAD(nh, sizeof(*ifi));

                    while(RTA_OK(rta, len)) {
                        switch(rta->rta_type) {
                        case IFLA_IFNAME:
                            char buffer[16 + IFNAMSIZ];
                            snprintf(buffer, sizeof(buffer), "INTERFACE=%s",
                                     (char *) RTA_DATA(rta));
                            mParams[0] = strdup(buffer);
                            mAction = (ifi->ifi_flags & IFF_LOWER_UP) ?
                              NlActionLinkUp : NlActionLinkDown;
                            mSubsystem = strdup("net");
                            break;
                        }

                        rta = RTA_NEXT(rta, len);
                    }
                }
            }
        }

        nh = NLMSG_NEXT(nh, size);
    }

    return true;
}

/* If the string between 'str' and 'end' begins with 'prefixlen' characters
/* If the string between 'str' and 'end' begins with 'prefixlen' characters
 * from the 'prefix' array, then return 'str + prefixlen', otherwise return
 * from the 'prefix' array, then return 'str + prefixlen', otherwise return
 * NULL.
 * NULL.
@@ -76,7 +128,11 @@ has_prefix(const char* str, const char* end, const char* prefix, size_t prefixle
#define HAS_CONST_PREFIX(str,end,prefix)  has_prefix((str),(end),prefix,CONST_STRLEN(prefix))
#define HAS_CONST_PREFIX(str,end,prefix)  has_prefix((str),(end),prefix,CONST_STRLEN(prefix))




bool NetlinkEvent::decode(char *buffer, int size) {
/*
 * Parse an ASCII-formatted message from a NETLINK_KOBJECT_UEVENT
 * netlink socket.
 */
bool NetlinkEvent::parseAsciiNetlinkMessage(char *buffer, int size) {
    const char *s = buffer;
    const char *s = buffer;
    const char *end;
    const char *end;
    int param_idx = 0;
    int param_idx = 0;
@@ -123,6 +179,14 @@ bool NetlinkEvent::decode(char *buffer, int size) {
    return true;
    return true;
}
}


bool NetlinkEvent::decode(char *buffer, int size, int format) {
    if (format == NetlinkListener::NETLINK_FORMAT_BINARY) {
        return parseBinaryNetlinkMessage(buffer, size);
    } else {
        return parseAsciiNetlinkMessage(buffer, size);
    }
}

const char *NetlinkEvent::findParam(const char *paramName) {
const char *NetlinkEvent::findParam(const char *paramName) {
    size_t len = strlen(paramName);
    size_t len = strlen(paramName);
    for (int i = 0; i < NL_PARAMS_MAX && mParams[i] != NULL; ++i) {
    for (int i = 0; i < NL_PARAMS_MAX && mParams[i] != NULL; ++i) {
+14 −5
Original line number Original line Diff line number Diff line
@@ -24,11 +24,21 @@
#include <cutils/log.h>
#include <cutils/log.h>
#include <cutils/uevent.h>
#include <cutils/uevent.h>


#include <sysutils/NetlinkListener.h>
#include <sysutils/NetlinkEvent.h>
#include <sysutils/NetlinkEvent.h>


#if 1
/* temporary version until we can get Motorola to update their
 * ril.so.  Their prebuilt ril.so is using this private class
 * so changing the NetlinkListener() constructor breaks their ril.
 */
NetlinkListener::NetlinkListener(int socket) :
NetlinkListener::NetlinkListener(int socket) :
                            SocketListener(socket, false) {
                            SocketListener(socket, false) {
    mFormat = NETLINK_FORMAT_ASCII;
}
#endif

NetlinkListener::NetlinkListener(int socket, int format) :
                            SocketListener(socket, false), mFormat(format) {
}
}


bool NetlinkListener::onDataAvailable(SocketClient *cli)
bool NetlinkListener::onDataAvailable(SocketClient *cli)
@@ -43,13 +53,12 @@ bool NetlinkListener::onDataAvailable(SocketClient *cli)
    }
    }


    NetlinkEvent *evt = new NetlinkEvent();
    NetlinkEvent *evt = new NetlinkEvent();
    if (!evt->decode(mBuffer, count)) {
    if (!evt->decode(mBuffer, count, mFormat)) {
        SLOGE("Error decoding NetlinkEvent");
        SLOGE("Error decoding NetlinkEvent");
        goto out;
    } else {
        onEvent(evt);
    }
    }


    onEvent(evt);
out:
    delete evt;
    delete evt;
    return true;
    return true;
}
}