Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Energy] Add radio states and energy consumption - Part 3 of RTEA #359

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 14 additions & 1 deletion cli/CmdRunner.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Copyright (c) 2020, The OTNS Authors.
// Copyright (c) 2022, The OTNS Authors.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
Expand Down Expand Up @@ -215,6 +215,8 @@ func (rt *CmdRunner) execute(cmd *Command, output io.Writer) {
rt.executeWeb(cc, cc.Web)
} else if cmd.NetInfo != nil {
rt.executeNetInfo(cc, cc.NetInfo)
} else if cmd.Energy != nil {
rt.executeEnergy(cc, cc.Energy)
} else {
simplelogger.Panicf("unimplemented command: %#v", cmd)
}
Expand Down Expand Up @@ -769,6 +771,17 @@ func (rt *CmdRunner) executeCoaps(cc *CommandContext, cmd *CoapsCmd) {
}
}

func (rt *CmdRunner) executeEnergy(cc *CommandContext, energy *EnergyCmd) {
if energy.Save != nil {
rt.postAsyncWait(func(sim *simulation.Simulation) {
sim.GetEnergyAnalyser().SaveEnergyDataToFile(energy.Name, sim.Dispatcher().CurTime)
})
} else {
cc.outputf("energy <command>\n")
cc.outputf("\tsave [output name]\n")
}
}

func NewCmdRunner(ctx *progctx.ProgCtx, sim *simulation.Simulation) *CmdRunner {
cr := &CmdRunner{
ctx: ctx,
Expand Down
15 changes: 14 additions & 1 deletion cli/ast.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Copyright (c) 2020, The OTNS Authors.
// Copyright (c) 2022, The OTNS Authors.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
Expand Down Expand Up @@ -60,6 +60,7 @@ type Command struct {
Speed *SpeedCmd `| @@` //nolint
Title *TitleCmd `| @@` //nolint
Web *WebCmd `| @@` //nolint
Energy *EnergyCmd `| @@` //nolint
}

//noinspection GoStructTag
Expand Down Expand Up @@ -327,6 +328,18 @@ type WebCmd struct {
Cmd struct{} `"web"` //nolint
}

//noinspection GoStructTag
type EnergyCmd struct {
Cmd struct{} `"energy"` //nolint
Save *SaveFlag `( @@ )?` //nolint
Name string `@String?` //nolint
}

//noinspection GoStructTag
type SaveFlag struct {
Dummy struct{} `"save"` //nolint
}

//noinspection GoStructTag
type RadioCmd struct {
Cmd struct{} `"radio"` //nolint
Expand Down
72 changes: 50 additions & 22 deletions dispatcher/Node.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Copyright (c) 2020, The OTNS Authors.
// Copyright (c) 2022, The OTNS Authors.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
Expand Down Expand Up @@ -40,6 +40,8 @@ import (
const (
maxPingResultCount = 1000
maxJoinResultCount = 1000
minChannel = 11
maxChannel = 26
)

type pingRequest struct {
Expand All @@ -65,15 +67,17 @@ type JoinResult struct {
}

type Node struct {
D *Dispatcher
Id NodeId
X, Y int
PartitionId uint32
ExtAddr uint64
Rloc16 uint16
CreateTime uint64
CurTime uint64
Role OtDeviceRole
D *Dispatcher
Id NodeId
X, Y int
PartitionId uint32
ExtAddr uint64
Rloc16 uint16
CreateTime uint64
CurTime uint64
Role OtDeviceRole
RadioState RadioStates
RadioChannel uint8

peerAddr *net.UDPAddr
failureCtrl *FailureCtrl
Expand All @@ -90,18 +94,19 @@ func newNode(d *Dispatcher, nodeid NodeId, x, y int, radioRange int) *Node {
simplelogger.AssertTrue(radioRange >= 0)

nc := &Node{
D: d,
Id: nodeid,
CurTime: d.CurTime,
CreateTime: d.CurTime,
X: x,
Y: y,
ExtAddr: InvalidExtAddr,
Rloc16: threadconst.InvalidRloc16,
Role: OtDeviceRoleDisabled,
peerAddr: nil, // peer address will be set when the first event is received
radioRange: radioRange,
joinerState: OtJoinerStateIdle,
D: d,
Id: nodeid,
CurTime: d.CurTime,
CreateTime: d.CurTime,
X: x,
Y: y,
ExtAddr: InvalidExtAddr,
Rloc16: threadconst.InvalidRloc16,
Role: OtDeviceRoleDisabled,
peerAddr: nil, // peer address will be set when the first event is received
radioRange: radioRange,
joinerState: OtJoinerStateIdle,
RadioChannel: minChannel,
}

nc.failureCtrl = newFailureCtrl(nc, NonFailTime)
Expand Down Expand Up @@ -300,3 +305,26 @@ func (node *Node) addJoinResult(js *joinerSession) {
node.joinResults = node.joinResults[1:]
}
}

func (node *Node) SetRadioStateFromString(s string, timestamp uint64) {
radioEnergy := node.D.energyAnalyser.GetNode(node.Id)

simplelogger.AssertNotNil(radioEnergy)

var state RadioStates
switch s {
case "off":
state = RadioDisabled
case "sleep":
state = RadioSleep
case "tx":
state = RadioTx
case "rx":
state = RadioRx
default:
simplelogger.Panicf("unknown radio state: %s", s)
}

node.RadioState = state
radioEnergy.SetRadioState(state, timestamp)
}
35 changes: 31 additions & 4 deletions dispatcher/dispatcher.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Copyright (c) 2020, The OTNS Authors.
// Copyright (c) 2022, The OTNS Authors.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
Expand Down Expand Up @@ -39,6 +39,7 @@ import (

"github.com/openthread/ot-ns/dissectpkt"
"github.com/openthread/ot-ns/dissectpkt/wpan"
"github.com/openthread/ot-ns/energy"
"github.com/openthread/ot-ns/pcap"
"github.com/openthread/ot-ns/threadconst"
"github.com/openthread/ot-ns/visualize"
Expand Down Expand Up @@ -138,8 +139,9 @@ type Dispatcher struct {
DispatchByShortAddrFail uint64
DispatchAllInRange uint64
}
watchingNodes map[NodeId]struct{}
stopped bool
watchingNodes map[NodeId]struct{}
energyAnalyser *energy.EnergyAnalyser
stopped bool
}

func NewDispatcher(ctx *progctx.ProgCtx, cfg *Config, cbHandler CallbackHandler) *Dispatcher {
Expand Down Expand Up @@ -718,6 +720,7 @@ func (d *Dispatcher) newNode(nodeid NodeId, x, y int, radioRange int) (node *Nod
node = newNode(d, nodeid, x, y, radioRange)
d.nodes[nodeid] = node
d.alarmMgr.AddNode(nodeid)
d.energyAnalyser.AddNode(nodeid, d.CurTime)
d.setAlive(nodeid)

d.vis.AddNode(nodeid, x, y, radioRange)
Expand Down Expand Up @@ -875,7 +878,8 @@ func (d *Dispatcher) handleStatusPush(srcid NodeId, data string) {
mode := ParseNodeMode(sp[1])
d.vis.SetNodeMode(srcid, mode)
} else if sp[0] == "radio_state" {
// TODO: calculate energy consumption based on radio state changes of each node
params := strings.Split(sp[1], ",")
d.changeNodeRadioState(srcid, params[0], params[1])
} else {
simplelogger.Warnf("unknown status push: %s=%s", sp[0], sp[1])
}
Expand Down Expand Up @@ -1033,6 +1037,10 @@ func (d *Dispatcher) advanceTime(ts uint64) {
elapsedRealTime := time.Since(d.speedStartRealTime) / time.Microsecond
if elapsedRealTime > 0 && ts/1000000 != oldTime/1000000 {
d.vis.AdvanceTime(ts, float64(elapsedTime)/float64(elapsedRealTime))

if d.energyAnalyser != nil && ts%energy.ComputePeriod == 0 {
d.energyAnalyser.StoreNetworkEnergy(ts)
}
}

if d.cfg.Real {
Expand Down Expand Up @@ -1129,6 +1137,7 @@ func (d *Dispatcher) DeleteNode(id NodeId) {
}
d.alarmMgr.DeleteNode(id)
d.deletedNodes[id] = struct{}{}
d.energyAnalyser.DeleteNode(id)

d.vis.DeleteNode(id)
}
Expand Down Expand Up @@ -1319,3 +1328,21 @@ func (d *Dispatcher) CollectCoapMessages() []*CoapMessage {
return nil
}
}

func (d *Dispatcher) SetEnergyAnalyser(e *energy.EnergyAnalyser) {
d.energyAnalyser = e
}

func (d *Dispatcher) changeNodeRadioState(nodeid NodeId, state, channel string) {
node := d.nodes[nodeid]

if d.energyAnalyser != nil {
node.SetRadioStateFromString(state, d.CurTime)
}

u, err := strconv.ParseUint(channel, 10, 8)
simplelogger.AssertNil(err, "changeNodeRadioState: invalid channel %s", channel)
simplelogger.AssertTrue(u >= minChannel && u <= maxChannel)

node.RadioChannel = uint8(u)
}
Loading