[posix] refine system initialization and deinitialization (#6886)

This commit refines system initialization and de-initialization by
separating the process before and after OpenThread instance creation
and destruction:

otSysInit():
  Call platformInit()
  Create OpenThread Instance as `gInstance`
  Call platformSetUp()

otSysDeinit():
  Call platformTearDown()
  Destroy OpenThread Instance `gInstance`
  Call platformDeinit()

This commit should help fix the issue that platform UDP sockets can
not be created when constructing OpenThread instance.

This commit contains other related changes:

- otSysDeinit now destroys the OpenThread instance

- posix/platform code use a global variable gInstance to track the
  single global OpenThread instance, instead of using multiple
  pointers in multiple files.
This commit is contained in:
Simon Lin
2021-08-12 15:01:32 -07:00
committed by GitHub
parent 02ff2110da
commit 59f7a9aed6
14 changed files with 308 additions and 162 deletions
+4 -4
View File
@@ -296,10 +296,9 @@ static otInstance *InitInstance(PosixConfig *aConfig)
IgnoreError(otLoggingSetLevel(aConfig->mLogLevel)); IgnoreError(otLoggingSetLevel(aConfig->mLogLevel));
instance = otSysInit(&aConfig->mPlatformConfig); instance = otSysInit(&aConfig->mPlatformConfig);
VerifyOrDie(instance != NULL, OT_EXIT_FAILURE);
syslog(LOG_INFO, "Thread interface: %s", otSysGetThreadNetifName()); syslog(LOG_INFO, "Thread interface: %s", otSysGetThreadNetifName());
atexit(otSysDeinit);
if (aConfig->mPrintRadioVersion) if (aConfig->mPrintRadioVersion)
{ {
printf("%s\n", otPlatRadioGetVersionString(instance)); printf("%s\n", otPlatRadioGetVersionString(instance));
@@ -324,9 +323,10 @@ void otTaskletsSignalPending(otInstance *aInstance)
void otPlatReset(otInstance *aInstance) void otPlatReset(otInstance *aInstance)
{ {
OT_UNUSED_VARIABLE(aInstance);
gPlatResetReason = OT_PLAT_RESET_REASON_SOFTWARE; gPlatResetReason = OT_PLAT_RESET_REASON_SOFTWARE;
otInstanceFinalize(aInstance);
otSysDeinit(); otSysDeinit();
longjmp(gResetJump, 1); longjmp(gResetJump, 1);
@@ -430,7 +430,7 @@ int main(int argc, char *argv[])
#endif #endif
exit: exit:
otInstanceFinalize(instance); otSysDeinit();
return rval; return rval;
} }
+13 -9
View File
@@ -46,10 +46,8 @@ unsigned int gBackboneNetifIndex = 0;
static ot::Posix::MulticastRoutingManager sMulticastRoutingManager; static ot::Posix::MulticastRoutingManager sMulticastRoutingManager;
#endif #endif
void platformBackboneInit(otInstance *aInstance, const char *aInterfaceName) void platformBackboneInit(const char *aInterfaceName)
{ {
OT_UNUSED_VARIABLE(aInstance);
VerifyOrExit(aInterfaceName != nullptr && aInterfaceName[0] != '\0'); VerifyOrExit(aInterfaceName != nullptr && aInterfaceName[0] != '\0');
VerifyOrDie(strnlen(aInterfaceName, sizeof(gBackboneNetifName)) < sizeof(gBackboneNetifName), VerifyOrDie(strnlen(aInterfaceName, sizeof(gBackboneNetifName)) < sizeof(gBackboneNetifName),
@@ -61,20 +59,26 @@ void platformBackboneInit(otInstance *aInstance, const char *aInterfaceName)
otLogInfoPlat("Backbone interface is configured to %s (%d)", gBackboneNetifName, gBackboneNetifIndex); otLogInfoPlat("Backbone interface is configured to %s (%d)", gBackboneNetifName, gBackboneNetifIndex);
#if OPENTHREAD_CONFIG_BACKBONE_ROUTER_MULTICAST_ROUTING_ENABLE
sMulticastRoutingManager.Init(aInstance);
#endif
exit: exit:
return; return;
} }
void platformBackboneDeinit(void) void platformBackboneSetUp(void)
{ {
#if OPENTHREAD_CONFIG_BACKBONE_ROUTER_MULTICAST_ROUTING_ENABLE #if OPENTHREAD_CONFIG_BACKBONE_ROUTER_MULTICAST_ROUTING_ENABLE
sMulticastRoutingManager.Deinit(); sMulticastRoutingManager.SetUp();
#endif #endif
}
void platformBackboneTearDown(void)
{
#if OPENTHREAD_CONFIG_BACKBONE_ROUTER_MULTICAST_ROUTING_ENABLE
sMulticastRoutingManager.TearDown();
#endif
}
void platformBackboneDeinit(void)
{
gBackboneNetifIndex = 0; gBackboneNetifIndex = 0;
memset(gBackboneNetifName, 0, sizeof(gBackboneNetifName)); memset(gBackboneNetifName, 0, sizeof(gBackboneNetifName));
+3 -3
View File
@@ -147,7 +147,7 @@ exit:
} }
} }
void Daemon::Enable(otInstance *aInstance) void Daemon::SetUp(void)
{ {
struct sockaddr_un sockname; struct sockaddr_un sockname;
int ret; int ret;
@@ -205,7 +205,7 @@ void Daemon::Enable(otInstance *aInstance)
} }
otCliInit( otCliInit(
aInstance, gInstance,
[](void *aContext, const char *aFormat, va_list aArguments) -> int { [](void *aContext, const char *aFormat, va_list aArguments) -> int {
return static_cast<Daemon *>(aContext)->OutputFormatV(aFormat, aArguments); return static_cast<Daemon *>(aContext)->OutputFormatV(aFormat, aArguments);
}, },
@@ -217,7 +217,7 @@ exit:
return; return;
} }
void Daemon::Disable(void) void Daemon::TearDown(void)
{ {
Mainloop::Manager::Get().Remove(*this); Mainloop::Manager::Get().Remove(*this);
+2 -2
View File
@@ -41,8 +41,8 @@ class Daemon : public Mainloop::Source, private NonCopyable
public: public:
static Daemon &Get(void); static Daemon &Get(void);
void Enable(otInstance *aInstance); void SetUp(void);
void Disable(void); void TearDown(void);
void Update(otSysMainloopContext &aContext) override; void Update(otSysMainloopContext &aContext) override;
void Process(const otSysMainloopContext &aContext) override; void Process(const otSysMainloopContext &aContext) override;
@@ -81,7 +81,8 @@ typedef struct otPlatformConfig
} otPlatformConfig; } otPlatformConfig;
/** /**
* This function performs all platform-specific initialization of OpenThread's drivers. * This function performs all platform-specific initialization of OpenThread's drivers and initializes the OpenThread
* instance.
* *
* @note This function is not called by the OpenThread library. Instead, the system/RTOS should call this function * @note This function is not called by the OpenThread library. Instead, the system/RTOS should call this function
* when initialization of OpenThread's drivers is most appropriate. * when initialization of OpenThread's drivers is most appropriate.
@@ -94,7 +95,8 @@ typedef struct otPlatformConfig
otInstance *otSysInit(otPlatformConfig *aPlatformConfig); otInstance *otSysInit(otPlatformConfig *aPlatformConfig);
/** /**
* This function performs all platform-specific deinitialization for OpenThread's drivers. * This function finalizes the OpenThread instance and performs all platform-specific deinitialization for OpenThread's
* drivers.
* *
* @note This function is not called by the OpenThread library. Instead, the system/RTOS should call this function * @note This function is not called by the OpenThread library. Instead, the system/RTOS should call this function
* when deinitialization of OpenThread's drivers is most appropriate. * when deinitialization of OpenThread's drivers is most appropriate.
+22 -8
View File
@@ -267,7 +267,7 @@ bool InfraNetif::IsRunning(void) const
return (ifReq.ifr_flags & IFF_RUNNING); return (ifReq.ifr_flags & IFF_RUNNING);
} }
void InfraNetif::Init(otInstance *aInstance, const char *aIfName) void InfraNetif::Init(const char *aIfName)
{ {
ssize_t rval; ssize_t rval;
uint32_t ifIndex = 0; uint32_t ifIndex = 0;
@@ -296,11 +296,27 @@ void InfraNetif::Init(otInstance *aInstance, const char *aIfName)
mNetLinkSocket = CreateNetLinkSocket(); mNetLinkSocket = CreateNetLinkSocket();
SuccessOrDie(otBorderRoutingInit(aInstance, ifIndex, platformInfraIfIsRunning())); exit:
SuccessOrDie(otBorderRoutingSetEnabled(aInstance, /* aEnabled */ true)); return;
}
mInstance = aInstance; void InfraNetif::SetUp(void)
{
OT_ASSERT(gInstance != nullptr);
VerifyOrExit(mInfraIfIndex != 0);
SuccessOrDie(otBorderRoutingInit(gInstance, mInfraIfIndex, platformInfraIfIsRunning()));
SuccessOrDie(otBorderRoutingSetEnabled(gInstance, /* aEnabled */ true));
Mainloop::Manager::Get().Add(*this); Mainloop::Manager::Get().Add(*this);
exit:
return;
}
void InfraNetif::TearDown(void)
{
VerifyOrExit(mInfraIfIndex != 0);
Mainloop::Manager::Get().Remove(*this);
exit: exit:
return; return;
@@ -308,8 +324,6 @@ exit:
void InfraNetif::Deinit(void) void InfraNetif::Deinit(void)
{ {
Mainloop::Manager::Get().Remove(*this);
if (mInfraIfIcmp6Socket != -1) if (mInfraIfIcmp6Socket != -1)
{ {
close(mInfraIfIcmp6Socket); close(mInfraIfIcmp6Socket);
@@ -369,7 +383,7 @@ void InfraNetif::ReceiveNetLinkMessage(void)
case RTM_DELADDR: case RTM_DELADDR:
case RTM_NEWLINK: case RTM_NEWLINK:
case RTM_DELLINK: case RTM_DELLINK:
SuccessOrDie(otPlatInfraIfStateChanged(mInstance, mInfraIfIndex, platformInfraIfIsRunning())); SuccessOrDie(otPlatInfraIfStateChanged(gInstance, mInfraIfIndex, platformInfraIfIsRunning()));
break; break;
case NLMSG_ERROR: case NLMSG_ERROR:
{ {
@@ -449,7 +463,7 @@ void InfraNetif::ReceiveIcmp6Message(void)
// the hoplimit must be 255 and the source address must be a link-local address. // the hoplimit must be 255 and the source address must be a link-local address.
VerifyOrExit(hopLimit == 255 && IN6_IS_ADDR_LINKLOCAL(&srcAddr.sin6_addr), error = OT_ERROR_DROP); VerifyOrExit(hopLimit == 255 && IN6_IS_ADDR_LINKLOCAL(&srcAddr.sin6_addr), error = OT_ERROR_DROP);
otPlatInfraIfRecvIcmp6Nd(mInstance, ifIndex, reinterpret_cast<otIp6Address *>(&srcAddr.sin6_addr), buffer, otPlatInfraIfRecvIcmp6Nd(gInstance, ifIndex, reinterpret_cast<otIp6Address *>(&srcAddr.sin6_addr), buffer,
bufferLength); bufferLength);
exit: exit:
+25 -7
View File
@@ -69,15 +69,34 @@ public:
/** /**
* This method initializes the infrastructure network interface. * This method initializes the infrastructure network interface.
* *
* @param[in] aInstance A pointer to an OpenThread instance. * @note This method is called before OpenThread instance is created.
*
* @param[in] aIfName A pointer to infrastructure network interface name. * @param[in] aIfName A pointer to infrastructure network interface name.
* *
*/ */
void Init(otInstance *aInstance, const char *aIfName); void Init(const char *aIfName);
/**
* This method sets up the infrastructure network interface.
*
* @note This method is called after OpenThread instance is created.
*
*/
void SetUp(void);
/**
* This method tears down the infrastructure network interface.
*
* @note This method is called before OpenThread instance is destructed.
*
*/
void TearDown(void);
/** /**
* This method deinitializes the infrastructure network interface. * This method deinitializes the infrastructure network interface.
* *
* @note This method is called after OpenThread instance is destructed.
*
*/ */
void Deinit(void); void Deinit(void);
@@ -117,11 +136,10 @@ public:
static InfraNetif &Get(void); static InfraNetif &Get(void);
private: private:
otInstance *mInstance; char mInfraIfName[IFNAMSIZ];
char mInfraIfName[IFNAMSIZ]; uint32_t mInfraIfIndex = 0;
uint32_t mInfraIfIndex = 0; int mInfraIfIcmp6Socket = -1;
int mInfraIfIcmp6Socket = -1; int mNetLinkSocket = -1;
int mNetLinkSocket = -1;
void ReceiveNetLinkMessage(void); void ReceiveNetLinkMessage(void);
void ReceiveIcmp6Message(void); void ReceiveIcmp6Message(void);
+9 -6
View File
@@ -46,24 +46,27 @@
#include <openthread/backbone_router_ftd.h> #include <openthread/backbone_router_ftd.h>
#include "core/common/debug.hpp"
#include "core/common/logging.hpp" #include "core/common/logging.hpp"
namespace ot { namespace ot {
namespace Posix { namespace Posix {
void MulticastRoutingManager::Init(otInstance *aInstance) void MulticastRoutingManager::SetUp(void)
{ {
mInstance = aInstance; OT_ASSERT(gInstance != nullptr);
otBackboneRouterSetMulticastListenerCallback(aInstance, otBackboneRouterSetMulticastListenerCallback(gInstance,
&MulticastRoutingManager::HandleBackboneMulticastListenerEvent, this); &MulticastRoutingManager::HandleBackboneMulticastListenerEvent, this);
Mainloop::Manager::Get().Add(*this); Mainloop::Manager::Get().Add(*this);
} }
void MulticastRoutingManager::Deinit(void) void MulticastRoutingManager::TearDown(void)
{ {
OT_ASSERT(gInstance != nullptr);
otBackboneRouterSetMulticastListenerCallback(gInstance, nullptr, nullptr);
Mainloop::Manager::Get().Remove(*this); Mainloop::Manager::Get().Remove(*this);
mInstance = nullptr;
} }
void MulticastRoutingManager::HandleBackboneMulticastListenerEvent(void * aContext, void MulticastRoutingManager::HandleBackboneMulticastListenerEvent(void * aContext,
@@ -136,7 +139,7 @@ bool MulticastRoutingManager::HasMulticastListener(const Ip6::Address &aAddress)
otBackboneRouterMulticastListenerIterator iter = OT_BACKBONE_ROUTER_MULTICAST_LISTENER_ITERATOR_INIT; otBackboneRouterMulticastListenerIterator iter = OT_BACKBONE_ROUTER_MULTICAST_LISTENER_ITERATOR_INIT;
otBackboneRouterMulticastListenerInfo listenerInfo; otBackboneRouterMulticastListenerInfo listenerInfo;
while (otBackboneRouterMulticastListenerGetNext(mInstance, &iter, &listenerInfo) == OT_ERROR_NONE) while (otBackboneRouterMulticastListenerGetNext(gInstance, &iter, &listenerInfo) == OT_ERROR_NONE)
{ {
VerifyOrExit(static_cast<const Ip6::Address &>(listenerInfo.mAddress) != aAddress, found = true); VerifyOrExit(static_cast<const Ip6::Address &>(listenerInfo.mAddress) != aAddress, found = true);
} }
+2 -3
View File
@@ -58,8 +58,8 @@ public:
{ {
} }
void Init(otInstance *aInstance); void SetUp(void);
void Deinit(void); void TearDown(void);
void Update(otSysMainloopContext &aContext) override; void Update(otSysMainloopContext &aContext) override;
void Process(const otSysMainloopContext &aContext) override; void Process(const otSysMainloopContext &aContext) override;
void HandleStateChange(otInstance *aInstance, otChangedFlags aFlags); void HandleStateChange(otInstance *aInstance, otChangedFlags aFlags);
@@ -134,7 +134,6 @@ private:
MulticastForwardingCache mMulticastForwardingCacheTable[kMulitcastForwardingCacheTableSize]; MulticastForwardingCache mMulticastForwardingCacheTable[kMulitcastForwardingCacheTableSize];
uint64_t mLastExpireTime; uint64_t mLastExpireTime;
int mMulticastRouterSock; int mMulticastRouterSock;
otInstance * mInstance;
}; };
} // namespace Posix } // namespace Posix
+64 -75
View File
@@ -145,9 +145,9 @@ extern int
#include <openthread/platform/misc.h> #include <openthread/platform/misc.h>
#include "common/code_utils.hpp" #include "common/code_utils.hpp"
#include "common/debug.hpp"
#include "common/logging.hpp" #include "common/logging.hpp"
#include "net/ip6_address.hpp" #include "net/ip6_address.hpp"
#include "posix/platform/udp.hpp"
unsigned int gNetifIndex = 0; unsigned int gNetifIndex = 0;
char gNetifName[IFNAMSIZ]; char gNetifName[IFNAMSIZ];
@@ -228,10 +228,9 @@ static otIp6Prefix sAddedExternalRoutes[kMaxExternalRoutesNum];
static otError destroyTunnel(void); static otError destroyTunnel(void);
#endif #endif
static otInstance *sInstance = nullptr; static int sTunFd = -1; ///< Used to exchange IPv6 packets.
static int sTunFd = -1; ///< Used to exchange IPv6 packets. static int sIpFd = -1; ///< Used to manage IPv6 stack on Thread interface.
static int sIpFd = -1; ///< Used to manage IPv6 stack on Thread interface. static int sNetlinkFd = -1; ///< Used to receive netlink events.
static int sNetlinkFd = -1; ///< Used to receive netlink events.
#if OPENTHREAD_POSIX_USE_MLD_MONITOR #if OPENTHREAD_POSIX_USE_MLD_MONITOR
static int sMLDMonitorFd = -1; ///< Used to receive MLD events. static int sMLDMonitorFd = -1; ///< Used to receive MLD events.
#endif #endif
@@ -392,7 +391,7 @@ static void UpdateUnicast(otInstance *aInstance, const otIp6AddressInfo &aAddres
{ {
OT_UNUSED_VARIABLE(aInstance); OT_UNUSED_VARIABLE(aInstance);
assert(sInstance == aInstance); assert(gInstance == aInstance);
assert(sIpFd >= 0); assert(sIpFd >= 0);
#if defined(__linux__) #if defined(__linux__)
@@ -442,7 +441,7 @@ static void UpdateMulticast(otInstance *aInstance, const otIp6Address &aAddress,
otError error = OT_ERROR_NONE; otError error = OT_ERROR_NONE;
int err; int err;
assert(sInstance == aInstance); assert(gInstance == aInstance);
VerifyOrExit(sIpFd >= 0); VerifyOrExit(sIpFd >= 0);
memcpy(&mreq.ipv6mr_multiaddr, &aAddress, sizeof(mreq.ipv6mr_multiaddr)); memcpy(&mreq.ipv6mr_multiaddr, &aAddress, sizeof(mreq.ipv6mr_multiaddr));
@@ -487,7 +486,7 @@ static void UpdateLink(otInstance *aInstance)
bool ifState = false; bool ifState = false;
bool otState = false; bool otState = false;
assert(sInstance == aInstance); assert(gInstance == aInstance);
VerifyOrExit(sIpFd >= 0); VerifyOrExit(sIpFd >= 0);
memset(&ifr, 0, sizeof(ifr)); memset(&ifr, 0, sizeof(ifr));
@@ -763,7 +762,7 @@ static void processReceive(otMessage *aMessage, void *aContext)
offset += 4; offset += 4;
#endif #endif
assert(sInstance == aContext); assert(gInstance == aContext);
assert(length <= kMaxIp6Size); assert(length <= kMaxIp6Size);
VerifyOrExit(sTunFd > 0); VerifyOrExit(sTunFd > 0);
@@ -802,7 +801,7 @@ static void processTransmit(otInstance *aInstance)
otError error = OT_ERROR_NONE; otError error = OT_ERROR_NONE;
size_t offset = 0; size_t offset = 0;
assert(sInstance == aInstance); assert(gInstance == aInstance);
rval = read(sTunFd, packet, sizeof(packet)); rval = read(sTunFd, packet, sizeof(packet));
VerifyOrExit(rval > 0, error = OT_ERROR_FAILED); VerifyOrExit(rval > 0, error = OT_ERROR_FAILED);
@@ -1335,41 +1334,6 @@ exit:
return; return;
} }
void platformNetifDeinit(void)
{
if (sTunFd != -1)
{
close(sTunFd);
sTunFd = -1;
#if defined(__NetBSD__) || defined(__FreeBSD__)
destroyTunnel();
#endif
}
if (sIpFd != -1)
{
close(sIpFd);
sIpFd = -1;
}
if (sNetlinkFd != -1)
{
close(sNetlinkFd);
sNetlinkFd = -1;
}
#if OPENTHREAD_POSIX_USE_MLD_MONITOR
if (sMLDMonitorFd != -1)
{
close(sMLDMonitorFd);
sMLDMonitorFd = -1;
}
#endif
gNetifIndex = 0;
}
#if OPENTHREAD_POSIX_USE_MLD_MONITOR #if OPENTHREAD_POSIX_USE_MLD_MONITOR
static void mldListenerInit(void) static void mldListenerInit(void)
{ {
@@ -1491,15 +1455,10 @@ exit:
#if defined(__linux__) #if defined(__linux__)
// set up the tun device // set up the tun device
static void platformConfigureTunDevice(otInstance *aInstance, static void platformConfigureTunDevice(const char *aInterfaceName, char *deviceName, size_t deviceNameLen)
const char *aInterfaceName,
char * deviceName,
size_t deviceNameLen)
{ {
struct ifreq ifr; struct ifreq ifr;
(void)aInstance;
sTunFd = open(OPENTHREAD_POSIX_TUN_DEVICE, O_RDWR | O_CLOEXEC | O_NONBLOCK); sTunFd = open(OPENTHREAD_POSIX_TUN_DEVICE, O_RDWR | O_CLOEXEC | O_NONBLOCK);
VerifyOrDie(sTunFd >= 0, OT_EXIT_ERROR_ERRNO); VerifyOrDie(sTunFd >= 0, OT_EXIT_ERROR_ERRNO);
@@ -1528,18 +1487,13 @@ static void platformConfigureTunDevice(otInstance *aInstance,
#endif #endif
#if defined(__APPLE__) && (OPENTHREAD_POSIX_CONFIG_MACOS_TUN_OPTION == OT_POSIX_CONFIG_MACOS_UTUN) #if defined(__APPLE__) && (OPENTHREAD_POSIX_CONFIG_MACOS_TUN_OPTION == OT_POSIX_CONFIG_MACOS_UTUN)
static void platformConfigureTunDevice(otInstance *aInstance, static void platformConfigureTunDevice(const char *aInterfaceName, char *deviceName, size_t deviceNameLen)
const char *aInterfaceName,
char * deviceName,
size_t deviceNameLen)
{ {
(void)aInterfaceName; (void)aInterfaceName;
int err = 0; int err = 0;
struct sockaddr_ctl addr; struct sockaddr_ctl addr;
struct ctl_info info; struct ctl_info info;
(void)aInstance;
sTunFd = SocketWithCloseExec(PF_SYSTEM, SOCK_DGRAM, SYSPROTO_CONTROL, kSocketNonBlock); sTunFd = SocketWithCloseExec(PF_SYSTEM, SOCK_DGRAM, SYSPROTO_CONTROL, kSocketNonBlock);
VerifyOrDie(sTunFd >= 0, OT_EXIT_ERROR_ERRNO); VerifyOrDie(sTunFd >= 0, OT_EXIT_ERROR_ERRNO);
@@ -1585,10 +1539,7 @@ exit:
#if defined(__NetBSD__) || \ #if defined(__NetBSD__) || \
(defined(__APPLE__) && (OPENTHREAD_POSIX_CONFIG_MACOS_TUN_OPTION == OT_POSIX_CONFIG_MACOS_TUN)) || \ (defined(__APPLE__) && (OPENTHREAD_POSIX_CONFIG_MACOS_TUN_OPTION == OT_POSIX_CONFIG_MACOS_TUN)) || \
defined(__FreeBSD__) defined(__FreeBSD__)
static void platformConfigureTunDevice(otInstance *aInstance, static void platformConfigureTunDevice(const char *aInterfaceName, char *deviceName, size_t deviceNameLen)
const char *aInterfaceName,
char * deviceName,
size_t deviceNameLen)
{ {
int flags = IFF_BROADCAST | IFF_MULTICAST; int flags = IFF_BROADCAST | IFF_MULTICAST;
int err; int err;
@@ -1596,7 +1547,6 @@ static void platformConfigureTunDevice(otInstance *aInstance,
const char *path; const char *path;
(void)aInterfaceName; (void)aInterfaceName;
(void)aInstance;
path = OPENTHREAD_POSIX_TUN_DEVICE; path = OPENTHREAD_POSIX_TUN_DEVICE;
@@ -1668,33 +1618,72 @@ static void platformConfigureNetLink(void)
#endif // defined(__APPLE__) || defined(__NetBSD__) || defined(__FreeBSD__) #endif // defined(__APPLE__) || defined(__NetBSD__) || defined(__FreeBSD__)
} }
void platformNetifInit(otInstance *aInstance, const char *aInterfaceName) void platformNetifInit(const char *aInterfaceName)
{ {
sIpFd = SocketWithCloseExec(AF_INET6, SOCK_DGRAM, IPPROTO_IP, kSocketNonBlock); sIpFd = SocketWithCloseExec(AF_INET6, SOCK_DGRAM, IPPROTO_IP, kSocketNonBlock);
VerifyOrDie(sIpFd >= 0, OT_EXIT_ERROR_ERRNO); VerifyOrDie(sIpFd >= 0, OT_EXIT_ERROR_ERRNO);
platformConfigureNetLink(); platformConfigureNetLink();
platformConfigureTunDevice(aInstance, aInterfaceName, gNetifName, sizeof(gNetifName)); platformConfigureTunDevice(aInterfaceName, gNetifName, sizeof(gNetifName));
gNetifIndex = if_nametoindex(gNetifName); gNetifIndex = if_nametoindex(gNetifName);
VerifyOrDie(gNetifIndex > 0, OT_EXIT_FAILURE); VerifyOrDie(gNetifIndex > 0, OT_EXIT_FAILURE);
#if OPENTHREAD_CONFIG_PLATFORM_UDP_ENABLE
ot::Posix::Udp::Get().Init(aInstance, gNetifName);
#endif
#if OPENTHREAD_POSIX_USE_MLD_MONITOR #if OPENTHREAD_POSIX_USE_MLD_MONITOR
mldListenerInit(); mldListenerInit();
#endif #endif
}
otIp6SetReceiveFilterEnabled(aInstance, true); void platformNetifSetUp(void)
otIcmp6SetEchoMode(aInstance, OT_ICMP6_ECHO_HANDLER_DISABLED); {
otIp6SetReceiveCallback(aInstance, processReceive, aInstance); OT_ASSERT(gInstance != nullptr);
otIp6SetAddressCallback(aInstance, processAddressChange, aInstance);
otIp6SetReceiveFilterEnabled(gInstance, true);
otIcmp6SetEchoMode(gInstance, OT_ICMP6_ECHO_HANDLER_DISABLED);
otIp6SetReceiveCallback(gInstance, processReceive, gInstance);
otIp6SetAddressCallback(gInstance, processAddressChange, gInstance);
#if OPENTHREAD_POSIX_MULTICAST_PROMISCUOUS_REQUIRED #if OPENTHREAD_POSIX_MULTICAST_PROMISCUOUS_REQUIRED
otIp6SetMulticastPromiscuousEnabled(aInstance, true); otIp6SetMulticastPromiscuousEnabled(aInstance, true);
#endif #endif
}
sInstance = aInstance; void platformNetifTearDown(void)
{
}
void platformNetifDeinit(void)
{
if (sTunFd != -1)
{
close(sTunFd);
sTunFd = -1;
#if defined(__NetBSD__) || defined(__FreeBSD__)
destroyTunnel();
#endif
}
if (sIpFd != -1)
{
close(sIpFd);
sIpFd = -1;
}
if (sNetlinkFd != -1)
{
close(sNetlinkFd);
sNetlinkFd = -1;
}
#if OPENTHREAD_POSIX_USE_MLD_MONITOR
if (sMLDMonitorFd != -1)
{
close(sMLDMonitorFd);
sMLDMonitorFd = -1;
}
#endif
gNetifIndex = 0;
} }
void platformNetifUpdateFdSet(fd_set *aReadFdSet, fd_set *aWriteFdSet, fd_set *aErrorFdSet, int *aMaxFd) void platformNetifUpdateFdSet(fd_set *aReadFdSet, fd_set *aWriteFdSet, fd_set *aErrorFdSet, int *aMaxFd)
@@ -1763,18 +1752,18 @@ void platformNetifProcess(const fd_set *aReadFdSet, const fd_set *aWriteFdSet, c
if (FD_ISSET(sTunFd, aReadFdSet)) if (FD_ISSET(sTunFd, aReadFdSet))
{ {
processTransmit(sInstance); processTransmit(gInstance);
} }
if (FD_ISSET(sNetlinkFd, aReadFdSet)) if (FD_ISSET(sNetlinkFd, aReadFdSet))
{ {
processNetlinkEvent(sInstance); processNetlinkEvent(gInstance);
} }
#if OPENTHREAD_POSIX_USE_MLD_MONITOR #if OPENTHREAD_POSIX_USE_MLD_MONITOR
if (FD_ISSET(sMLDMonitorFd, aReadFdSet)) if (FD_ISSET(sMLDMonitorFd, aReadFdSet))
{ {
processMLDEvent(sInstance); processMLDEvent(gInstance);
} }
#endif #endif
+58 -10
View File
@@ -171,12 +171,6 @@ void platformRadioInit(const char *aUrl);
*/ */
void platformRadioDeinit(void); void platformRadioDeinit(void);
/**
* This function shuts down platform network interface.
*
*/
void platformNetifDeinit(void);
/** /**
* This function inputs a received radio frame. * This function inputs a received radio frame.
* *
@@ -245,11 +239,38 @@ void platformUartProcess(const fd_set *aReadFdSet, const fd_set *aWriteFdSet, co
/** /**
* This function initializes platform netif. * This function initializes platform netif.
* *
* @param[in] aInstance A pointer to the OpenThread instance. * @note This function is called before OpenThread instance is created.
*
* @param[in] aInterfaceName A pointer to Thread network interface name. * @param[in] aInterfaceName A pointer to Thread network interface name.
* *
*/ */
void platformNetifInit(otInstance *aInstance, const char *aInterfaceName); void platformNetifInit(const char *aInterfaceName);
/**
* This function sets up platform netif.
*
* @note This function is called after OpenThread instance is created.
*
* @param[in] aInstance A pointer to the OpenThread instance.
*
*/
void platformNetifSetUp(void);
/**
* This function tears down platform netif.
*
* @note This function is called before OpenThread instance is destructed.
*
*/
void platformNetifTearDown(void);
/**
* This function deinitializes platform netif.
*
* @note This function is called after OpenThread instance is destructed.
*
*/
void platformNetifDeinit(void);
/** /**
* This function updates the file descriptor sets with file descriptors used by platform netif module. * This function updates the file descriptor sets with file descriptors used by platform netif module.
@@ -430,15 +451,36 @@ extern unsigned int gNetifIndex;
/** /**
* This function initializes platform Backbone network. * This function initializes platform Backbone network.
* *
* @param[in] aInstance A pointer to the OpenThread instance. * @note This function is called before OpenThread instance is created.
*
* @param[in] aInterfaceName A pointer to Thread network interface name. * @param[in] aInterfaceName A pointer to Thread network interface name.
* *
*/ */
void platformBackboneInit(otInstance *aInstance, const char *aInterfaceName); void platformBackboneInit(const char *aInterfaceName);
/**
* This function sets up platform Backbone network.
*
* @note This function is called after OpenThread instance is created.
*
* @param[in] aInstance A pointer to the OpenThread instance.
*
*/
void platformBackboneSetUp(void);
/**
* This function tears down platform Backbone network.
*
* @note This function is called before OpenThread instance is destructed.
*
*/
void platformBackboneTearDown(void);
/** /**
* This function shuts down the platform Backbone network. * This function shuts down the platform Backbone network.
* *
* @note This function is called after OpenThread instance is destructed.
*
*/ */
void platformBackboneDeinit(void); void platformBackboneDeinit(void);
@@ -451,6 +493,12 @@ void platformBackboneDeinit(void);
*/ */
void platformBackboneStateChange(otInstance *aInstance, otChangedFlags aFlags); void platformBackboneStateChange(otInstance *aInstance, otChangedFlags aFlags);
/**
* A pointer to the OpenThread instance.
*
*/
extern otInstance *gInstance;
/** /**
* The name of Backbone network interface. * The name of Backbone network interface.
* *
+87 -21
View File
@@ -47,12 +47,15 @@
#include <openthread/platform/radio.h> #include <openthread/platform/radio.h>
#include "common/code_utils.hpp" #include "common/code_utils.hpp"
#include "common/debug.hpp"
#include "posix/platform/daemon.hpp" #include "posix/platform/daemon.hpp"
#include "posix/platform/infra_if.hpp" #include "posix/platform/infra_if.hpp"
#include "posix/platform/mainloop.hpp" #include "posix/platform/mainloop.hpp"
#include "posix/platform/radio_url.hpp" #include "posix/platform/radio_url.hpp"
#include "posix/platform/udp.hpp" #include "posix/platform/udp.hpp"
otInstance *gInstance = nullptr;
#if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE || OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE #if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE || OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE
static void processStateChange(otChangedFlags aFlags, void *aContext) static void processStateChange(otChangedFlags aFlags, void *aContext)
{ {
@@ -115,10 +118,8 @@ static const char *getTrelRadioUrl(otPlatformConfig *aPlatformConfig)
} }
#endif #endif
otInstance *otSysInit(otPlatformConfig *aPlatformConfig) void platformInit(otPlatformConfig *aPlatformConfig)
{ {
otInstance *instance = nullptr;
platformAlarmInit(aPlatformConfig->mSpeedUpFactor, aPlatformConfig->mRealTimeSignal); platformAlarmInit(aPlatformConfig->mSpeedUpFactor, aPlatformConfig->mRealTimeSignal);
platformRadioInit(get802154RadioUrl(aPlatformConfig)); platformRadioInit(get802154RadioUrl(aPlatformConfig));
#if OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE #if OPENTHREAD_CONFIG_RADIO_LINK_TREL_ENABLE
@@ -126,40 +127,95 @@ otInstance *otSysInit(otPlatformConfig *aPlatformConfig)
#endif #endif
platformRandomInit(); platformRandomInit();
instance = otInstanceInitSingle();
assert(instance != nullptr);
#if OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE #if OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE
platformBackboneInit(instance, aPlatformConfig->mBackboneInterfaceName); platformBackboneInit(aPlatformConfig->mBackboneInterfaceName);
#endif #endif
#if OPENTHREAD_CONFIG_BORDER_ROUTING_ENABLE #if OPENTHREAD_CONFIG_BORDER_ROUTING_ENABLE
ot::Posix::InfraNetif::Get().Init(instance, aPlatformConfig->mBackboneInterfaceName); ot::Posix::InfraNetif::Get().Init(aPlatformConfig->mBackboneInterfaceName);
#endif
gNetifName[0] = '\0';
#if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE
platformNetifInit(aPlatformConfig->mInterfaceName);
#endif
#if OPENTHREAD_CONFIG_PLATFORM_UDP_ENABLE
#if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE
ot::Posix::Udp::Get().Init(otSysGetThreadNetifName());
#else
ot::Posix::Udp::Get().Init(aPlatformConfig->mInterfaceName);
#endif
#endif
}
void platformSetUp(void)
{
#if OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE
platformBackboneSetUp();
#endif
#if OPENTHREAD_CONFIG_BORDER_ROUTING_ENABLE
ot::Posix::InfraNetif::Get().SetUp();
#endif #endif
#if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE #if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE
platformNetifInit(instance, aPlatformConfig->mInterfaceName); platformNetifSetUp();
#elif OPENTHREAD_CONFIG_PLATFORM_UDP_ENABLE #endif
ot::Posix::Udp::Get().Init(instance, aPlatformConfig->mInterfaceName);
#else #if OPENTHREAD_CONFIG_PLATFORM_UDP_ENABLE
gNetifName[0] = '\0'; ot::Posix::Udp::Get().SetUp();
#endif
#if OPENTHREAD_POSIX_CONFIG_DAEMON_ENABLE
ot::Posix::Daemon::Get().SetUp();
#endif #endif
#if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE || OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE #if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE || OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE
SuccessOrDie(otSetStateChangedCallback(instance, processStateChange, instance)); SuccessOrDie(otSetStateChangedCallback(gInstance, processStateChange, gInstance));
#endif #endif
#if OPENTHREAD_POSIX_CONFIG_DAEMON_ENABLE
ot::Posix::Daemon::Get().Enable(instance);
#endif
return instance;
} }
void otSysDeinit(void) otInstance *otSysInit(otPlatformConfig *aPlatformConfig)
{
OT_ASSERT(gInstance == nullptr);
platformInit(aPlatformConfig);
gInstance = otInstanceInitSingle();
OT_ASSERT(gInstance != nullptr);
platformSetUp();
return gInstance;
}
void platformTearDown(void)
{ {
#if OPENTHREAD_POSIX_CONFIG_DAEMON_ENABLE #if OPENTHREAD_POSIX_CONFIG_DAEMON_ENABLE
ot::Posix::Daemon::Get().Disable(); ot::Posix::Daemon::Get().TearDown();
#endif #endif
#if OPENTHREAD_CONFIG_PLATFORM_UDP_ENABLE
ot::Posix::Udp::Get().TearDown();
#endif
#if OPENTHREAD_CONFIG_PLATFORM_NETIF_ENABLE
platformNetifTearDown();
#endif
#if OPENTHREAD_CONFIG_BORDER_ROUTING_ENABLE
ot::Posix::InfraNetif::Get().TearDown();
#endif
#if OPENTHREAD_CONFIG_BACKBONE_ROUTER_ENABLE
platformBackboneTearDown();
#endif
}
void platformDeinit(void)
{
#if OPENTHREAD_POSIX_VIRTUAL_TIME #if OPENTHREAD_POSIX_VIRTUAL_TIME
virtualTimeDeinit(); virtualTimeDeinit();
#endif #endif
@@ -183,6 +239,16 @@ void otSysDeinit(void)
#endif #endif
} }
void otSysDeinit(void)
{
OT_ASSERT(gInstance != nullptr);
platformTearDown();
otInstanceFinalize(gInstance);
gInstance = nullptr;
platformDeinit();
}
#if OPENTHREAD_POSIX_VIRTUAL_TIME #if OPENTHREAD_POSIX_VIRTUAL_TIME
/** /**
* This function try selecting the given file descriptors in nonblocking mode. * This function try selecting the given file descriptors in nonblocking mode.
+12 -8
View File
@@ -550,7 +550,7 @@ void Udp::Update(otSysMainloopContext &aContext)
{ {
VerifyOrExit(gNetifIndex != 0); VerifyOrExit(gNetifIndex != 0);
for (otUdpSocket *socket = otUdpGetSockets(mInstance); socket != nullptr; socket = socket->mNext) for (otUdpSocket *socket = otUdpGetSockets(gInstance); socket != nullptr; socket = socket->mNext)
{ {
int fd; int fd;
@@ -572,7 +572,7 @@ exit:
return; return;
} }
void Udp::Init(otInstance *aInstance, const char *aIfName) void Udp::Init(const char *aIfName)
{ {
if (aIfName == nullptr) if (aIfName == nullptr)
{ {
@@ -589,17 +589,21 @@ void Udp::Init(otInstance *aInstance, const char *aIfName)
} }
assert(gNetifIndex != 0); assert(gNetifIndex != 0);
}
mInstance = aInstance; void Udp::SetUp(void)
{
Mainloop::Manager::Get().Add(*this); Mainloop::Manager::Get().Add(*this);
} }
void Udp::TearDown(void)
{
Mainloop::Manager::Get().Remove(*this);
}
void Udp::Deinit(void) void Udp::Deinit(void)
{ {
// TODO All platform sockets should be closed // TODO All platform sockets should be closed
mInstance = nullptr;
Mainloop::Manager::Get().Remove(*this);
} }
Udp &Udp::Get(void) Udp &Udp::Get(void)
@@ -613,7 +617,7 @@ void Udp::Process(const otSysMainloopContext &aContext)
{ {
otMessageSettings msgSettings = {false, OT_MESSAGE_PRIORITY_NORMAL}; otMessageSettings msgSettings = {false, OT_MESSAGE_PRIORITY_NORMAL};
for (otUdpSocket *socket = otUdpGetSockets(mInstance); socket != nullptr; socket = socket->mNext) for (otUdpSocket *socket = otUdpGetSockets(gInstance); socket != nullptr; socket = socket->mNext)
{ {
int fd = FdFromHandle(socket->mHandle); int fd = FdFromHandle(socket->mHandle);
@@ -632,7 +636,7 @@ void Udp::Process(const otSysMainloopContext &aContext)
continue; continue;
} }
message = otUdpNewMessage(mInstance, &msgSettings); message = otUdpNewMessage(gInstance, &msgSettings);
if (message == nullptr) if (message == nullptr)
{ {
+3 -4
View File
@@ -39,13 +39,12 @@ class Udp : public Mainloop::Source, private NonCopyable
public: public:
static Udp &Get(void); static Udp &Get(void);
void Init(otInstance *aInstance, const char *aIfName); void Init(const char *aIfName);
void SetUp(void);
void TearDown(void);
void Deinit(void); void Deinit(void);
void Update(otSysMainloopContext &aContext) override; void Update(otSysMainloopContext &aContext) override;
void Process(const otSysMainloopContext &aContext) override; void Process(const otSysMainloopContext &aContext) override;
private:
otInstance *mInstance = nullptr;
}; };
} // namespace Posix } // namespace Posix