mirror of
https://github.com/espressif/openthread.git
synced 2026-08-05 02:17:47 +00:00
[nexus] add support for writing test_info.json (#12355)
This commit adds support for writing test_info.json in the Nexus platform. The test_info.json file contains information about the test topology, including node names, roles, and addresses. This information is used by the packet verification framework to verify the behavior of the network. Changes: - Added `Core::SaveTestInfo` to `nexus_core.cpp` to write node information to JSON. - Added `SetName` and `GetName` to `Node` class in `nexus_node.hpp`. - Updated `test_5_1_1.cpp` to set node names and call `SaveTestInfo`.
This commit is contained in:
@@ -29,6 +29,7 @@
|
||||
#include "nexus_core.hpp"
|
||||
|
||||
#include <cstdlib>
|
||||
#include <cstring>
|
||||
|
||||
#include "nexus_node.hpp"
|
||||
|
||||
@@ -59,6 +60,153 @@ Core::Core(void)
|
||||
}
|
||||
}
|
||||
|
||||
void Core::SaveTestInfo(const char *aFilename)
|
||||
{
|
||||
FILE *file = fopen(aFilename, "w");
|
||||
Node *tail = mNodes.GetTail();
|
||||
const char *testcase;
|
||||
const char *slash;
|
||||
const char *dot;
|
||||
const char *version;
|
||||
int testcaseLen;
|
||||
|
||||
VerifyOrExit(file != nullptr);
|
||||
|
||||
testcase = aFilename;
|
||||
slash = strrchr(aFilename, '/');
|
||||
|
||||
if (slash != nullptr)
|
||||
{
|
||||
testcase = slash + 1;
|
||||
}
|
||||
|
||||
dot = strrchr(testcase, '.');
|
||||
testcaseLen = (dot != nullptr) ? static_cast<int>(dot - testcase) : static_cast<int>(strlen(testcase));
|
||||
|
||||
switch (otThreadGetVersion())
|
||||
{
|
||||
case OT_THREAD_VERSION_1_1:
|
||||
version = "1.1";
|
||||
break;
|
||||
case OT_THREAD_VERSION_1_2:
|
||||
version = "1.2";
|
||||
break;
|
||||
case OT_THREAD_VERSION_1_3:
|
||||
version = "1.3";
|
||||
break;
|
||||
case OT_THREAD_VERSION_1_4:
|
||||
version = "1.4";
|
||||
break;
|
||||
default:
|
||||
version = "unknown";
|
||||
break;
|
||||
}
|
||||
|
||||
fprintf(file, "{\n");
|
||||
fprintf(file, " \"testcase\": \"%.*s\",\n", testcaseLen, testcase);
|
||||
fprintf(file, " \"pcap\": \"%s\",\n", getenv("OT_NEXUS_PCAP_FILE") ? getenv("OT_NEXUS_PCAP_FILE") : "");
|
||||
|
||||
if (!mNodes.IsEmpty())
|
||||
{
|
||||
NetworkKey networkKey;
|
||||
Node &node = *mNodes.GetHead();
|
||||
String<OT_NETWORK_KEY_SIZE * 2 + 1> keyString;
|
||||
|
||||
node.Get<KeyManager>().GetNetworkKey(networkKey);
|
||||
keyString.AppendHexBytes(networkKey.m8, OT_NETWORK_KEY_SIZE);
|
||||
fprintf(file, " \"network_key\": \"%s\",\n", keyString.AsCString());
|
||||
|
||||
for (Node &leaderNode : mNodes)
|
||||
{
|
||||
if (leaderNode.Get<Mle::Mle>().IsLeader())
|
||||
{
|
||||
Ip6::Address aloc;
|
||||
leaderNode.Get<Mle::Mle>().GetLeaderAloc(aloc);
|
||||
fprintf(file, " \"leader_aloc\": \"%s\",\n", aloc.ToString().AsCString());
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fprintf(file, " \"topology\": {\n");
|
||||
for (Node &node : mNodes)
|
||||
{
|
||||
fprintf(file, " \"%u\": {\"name\": \"%s\", \"version\": \"%s\"}%s\n", node.GetInstance().GetId(),
|
||||
node.GetName() ? node.GetName() : "", version, (&node == tail) ? "" : ",");
|
||||
}
|
||||
fprintf(file, " },\n");
|
||||
|
||||
fprintf(file, " \"extaddrs\": {\n");
|
||||
for (Node &node : mNodes)
|
||||
{
|
||||
fprintf(file, " \"%u\": \"%s\"%s\n", node.GetInstance().GetId(),
|
||||
node.Get<Mac::Mac>().GetExtAddress().ToString().AsCString(), (&node == tail) ? "" : ",");
|
||||
}
|
||||
fprintf(file, " },\n");
|
||||
|
||||
fprintf(file, " \"rloc16s\": {\n");
|
||||
for (Node &node : mNodes)
|
||||
{
|
||||
fprintf(file, " \"%u\": \"0x%04x\"%s\n", node.GetInstance().GetId(), node.Get<Mle::Mle>().GetRloc16(),
|
||||
(&node == tail) ? "" : ",");
|
||||
}
|
||||
fprintf(file, " },\n");
|
||||
|
||||
fprintf(file, " \"mleids\": {\n");
|
||||
for (Node &node : mNodes)
|
||||
{
|
||||
fprintf(file, " \"%u\": \"%s\"%s\n", node.GetInstance().GetId(),
|
||||
node.Get<Mle::Mle>().GetMeshLocalEid().ToString().AsCString(), (&node == tail) ? "" : ",");
|
||||
}
|
||||
fprintf(file, " },\n");
|
||||
|
||||
fprintf(file, " \"rlocs\": {\n");
|
||||
for (Node &node : mNodes)
|
||||
{
|
||||
fprintf(file, " \"%u\": \"%s\"%s\n", node.GetInstance().GetId(),
|
||||
node.Get<Mle::Mle>().GetMeshLocalRloc().ToString().AsCString(), (&node == tail) ? "" : ",");
|
||||
}
|
||||
fprintf(file, " },\n");
|
||||
|
||||
fprintf(file, " \"ipaddrs\": {\n");
|
||||
for (Node &node : mNodes)
|
||||
{
|
||||
bool first = true;
|
||||
|
||||
fprintf(file, " \"%u\": [\n", node.GetInstance().GetId());
|
||||
for (const Ip6::Netif::UnicastAddress &addr : node.Get<ThreadNetif>().GetUnicastAddresses())
|
||||
{
|
||||
if (!first)
|
||||
{
|
||||
fprintf(file, ",\n");
|
||||
}
|
||||
fprintf(file, " \"%s\"", addr.GetAddress().ToString().AsCString());
|
||||
first = false;
|
||||
}
|
||||
fprintf(file, "\n ]%s\n", (&node == tail) ? "" : ",");
|
||||
}
|
||||
fprintf(file, " },\n");
|
||||
|
||||
fprintf(file, " \"extra_vars\": {\n");
|
||||
if (!mNodes.IsEmpty())
|
||||
{
|
||||
Node &node = *mNodes.GetHead();
|
||||
Ip6::Prefix prefix;
|
||||
|
||||
prefix.Set(node.Get<Mle::Mle>().GetMeshLocalPrefix());
|
||||
fprintf(file, " \"mesh_local_prefix\": \"%s\"\n", prefix.ToString().AsCString());
|
||||
}
|
||||
fprintf(file, " }\n");
|
||||
|
||||
fprintf(file, "}\n");
|
||||
|
||||
exit:
|
||||
if (file != nullptr)
|
||||
{
|
||||
fclose(file);
|
||||
}
|
||||
}
|
||||
|
||||
Core::~Core(void) { sInUse = false; }
|
||||
|
||||
Node &Core::CreateNode(void)
|
||||
|
||||
@@ -56,6 +56,8 @@ public:
|
||||
TimeMilli GetNow(void) { return mNow; }
|
||||
void AdvanceTime(uint32_t aDuration);
|
||||
|
||||
void SaveTestInfo(const char *aFilename);
|
||||
|
||||
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
// Used by platform implementation
|
||||
|
||||
|
||||
@@ -83,6 +83,9 @@ public:
|
||||
void GetTrelSockAddr(Ip6::SockAddr &aSockAddr) const;
|
||||
#endif
|
||||
|
||||
void SetName(const char *aName) { IgnoreError(StringCopy(mName, aName)); }
|
||||
const char *GetName(void) const { return mName; }
|
||||
|
||||
//- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
|
||||
|
||||
template <typename Type> Type &Get(void)
|
||||
@@ -113,7 +116,9 @@ public:
|
||||
Node *mNext;
|
||||
|
||||
private:
|
||||
Node(void) = default;
|
||||
Node(void) {}
|
||||
|
||||
char mName[32];
|
||||
};
|
||||
|
||||
inline Node &AsNode(otInstance *aInstance) { return Node::From(aInstance); }
|
||||
|
||||
@@ -106,6 +106,9 @@ void Test5_1_1(void)
|
||||
Node &leader = nexus.CreateNode();
|
||||
Node &router = nexus.CreateNode();
|
||||
|
||||
leader.SetName("LEADER");
|
||||
router.SetName("ROUTER");
|
||||
|
||||
nexus.AdvanceTime(0);
|
||||
|
||||
Instance::SetLogLevel(kLogLevelInfo);
|
||||
@@ -194,6 +197,8 @@ void Test5_1_1(void)
|
||||
router.Get<Mle::Mle>().GetLinkLocalAddress().ToString().AsCString());
|
||||
SendAndVerifyEchoRequest(nexus, leader, router, leaderReceivedEchoReply);
|
||||
Log("Router (as DUT) responded with Echo Reply successfully");
|
||||
|
||||
nexus.SaveTestInfo("test_5_1_1.json");
|
||||
}
|
||||
|
||||
} // namespace Nexus
|
||||
|
||||
Reference in New Issue
Block a user