Skip to content

Instantly share code, notes, and snippets.

@MurphyMc
Created March 23, 2015 20:39
Show Gist options
  • Select an option

  • Save MurphyMc/606ab7e71f49f4fb4a58 to your computer and use it in GitHub Desktop.

Select an option

Save MurphyMc/606ab7e71f49f4fb4a58 to your computer and use it in GitHub Desktop.
# Copyright 2015 James McCauley
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at:
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
"""
CPU-utilization-based server load balancer
This is a hacky component which balances load across servers according to their
CPU utilization. The hackiest parts are due to how it has to override some
of the behavior of ip_loadbalancer, which could use a little refactoring to
make doing this easier.
Relies on the servers running POX with the cpu_agent component.
On the controller, you want to run something like...
./pox.py messenger cpu_loadbalancer --ip=10.0.0.1 --servers=10.0.0.2,10.0.0.3
Then on each server, you want to run something like...
./pox.py messenger messenger.tcp_transport cpu_agent
Note that this is totally untested and isn't suitable for real-world use.
It's just a little example.
"""
from pox.core import core
from pox.messenger.tcp_transport import ActiveTCPTransport
import pox.misc.ip_loadbalancer
# ip_loadbalancer's launch() function does a lot of stuff. We could cut
# and paste it here, or we could actually refactor it properly. But
# for the moment, let's just swap out the original load balancer and
# put in our CPU-aware one instead...
old_iplb = pox.misc.ip_loadbalancer.iplb
class CPUBalancer (old_iplb):
"""
A least-loaded-first server load balancer
Based on CPU utilization information gathered by a remote agent, assigns
traffic to the least loaded machine.
"""
_core_name = 'iplb'
utilizations = {} # Populated in ugly way by CPUMonitorClient
def _pick_server (self, key, inport):
servers = set(self.live_servers.keys())
servers.intersection_update(self.utilizations.keys())
servers = [(self.utilizations[ip],ip) for ip in servers]
servers.sort()
if not servers:
# It'd be nice if we could return None, but it's currently not allowed.
return self.live_servers.keys()[0]
return servers[0][1]
# Swap it in...
pox.misc.ip_loadbalancer.iplb = CPUBalancer
class CPUMonitorClient (object):
"""
A component that monitors external CPU agents
Connects to cpu_agent instances on servers via messenger, gathers the
reported CPU utilization information, and relays it to CPUBalancer.
"""
def __init__ (self, servers):
core.listen_to_dependencies(self)
self.servers = servers
def _all_dependencies_met (self):
self.channel = core.MessengerNexus.get_channel("CPU")
self.channel.addListenerByName("MessageReceived", self._rx_CPU)
# Fire up messenger connections to all of the servers...
for server in self.servers:
t = ActiveTCPTransport(server) # Use default port
t.start()
def _handle_MessengerNexus_ConnectionOpened (self, event):
# On connect, join the CPU channel
event.con.send({"CHANNEL":"", "cmd":"join_channel", "channel":"CPU"})
def _rx_CPU (self, event, data):
# We steal the IP address out of the transport, thus we can only work with
# certain transports. Of course, we just started the expected transports
# above, and they ARE all the right type...
if not isinstance(event.con._transport, ActiveTCPTransport): return
ip = event.con._transport._addr[0]
util = data.get('utilization', 0.5)
if core.hasComponent('iplb'):
core.iplb.utilizations[ip] = util
def launch (ip, servers, dpid = None):
core.registerNew(CPUMonitorClient, servers.replace(","," ").split())
pox.misc.ip_loadbalancer.launch(ip, servers, dpid)
@SadhuRamBasnet
Copy link

Hello Murphy,

Where to put cpu_loadbalancer.py? which directory?

Regards
Sadhu Ram Basnet
Nepal

@SadhuRamBasnet
Copy link

@gtomy200
Copy link

gtomy200 commented Dec 2, 2017

Hello Murphy,

When i'm trying to run your code its throwing import error for "ActiveTCPTransport". Did u install any specific package.

@MurphyMc
Copy link
Author

MurphyMc commented Mar 5, 2019

This is a POX component, so some of the questions surrounding it can probably be answered by looking at the POX documentation.

The short version is that this is a POX component meant to be used along with cpu_agent.py. Put them somewhere POX can find them; the easiest thing is just to put them in POX's ext/ directory. Then the commandline given in the docstring should hopefully work.

I don't remember which version of POX this was written for, so you may need to play around a bit. Probably something back from around when the gist was created (in 2015). But hopefully it'll work on more current versions too.

@raghdaaljaff
Copy link

Hello @MurphyMc brother can you tell me about how to use the cpu_agent .py , I saw the docstring that told to use on each server
and I used at first the cpu_loadbalancer.py on the controller
and create topology in mininet but when I wrote pingall the controller not connect to topology and I don’t know where I put the cpu_agent.py , I tried put it in the spartely terminal after I wrote cd pox
sudo ./pox.py messenger messenger .tcp_transport cpu_agent
But the error appear that the module cpu_agent not find , although I put the cpu_agent inside pox/messenger
any help me please

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment