Toggle navigation
Toggle navigation
This project
Loading...
Sign in
홍길동
/
onos
Go to a project
Toggle navigation
Toggle navigation pinning
Projects
Groups
Snippets
Help
Project
Activity
Repository
Pipelines
Graphs
Issues
0
Merge Requests
0
Wiki
Snippets
Network
Create a new issue
Builds
Commits
Issue Boards
Authored by
alshabib
2014-09-09 11:53:19 -0700
Browse Files
Options
Browse Files
Download
Email Patches
Plain Diff
Commit
df652addd12217d5d9c6f60cf8805aae22b57533
df652add
1 parent
1d334ce8
link discovery and providers are implemented
Hide whitespace changes
Inline
Side-by-side
Showing
14 changed files
with
792 additions
and
282 deletions
net/api/src/main/java/org/onlab/onos/net/ConnectPoint.java
net/core/trivial/src/main/java/org/onlab/onos/net/trivial/impl/SimpleLinkManager.java
of/api/src/main/java/org/onlab/onos/of/controller/DefaultPacketContext.java
of/api/src/main/java/org/onlab/onos/of/controller/PacketContext.java
of/ctl/src/main/java/org/onlab/onos/of/controller/impl/OFChannelHandler.java
of/ctl/src/main/java/org/onlab/onos/of/controller/impl/OpenFlowControllerImpl.java
of/ctl/src/main/java/org/onlab/onos/of/controller/impl/RoleManager.java
of/ctl/src/main/java/org/onlab/onos/of/drivers/impl/OFSwitchImplOVS10.java
pom.xml
providers/of/link/src/main/java/org/onlab/onos/provider/of/link/impl/LinkDiscovery.java
providers/of/link/src/main/java/org/onlab/onos/provider/of/link/impl/OpenFlowLinkProvider.java
utils/misc/pom.xml
utils/misc/src/main/java/org/onlab/packet/ONLabLddp.java
utils/misc/src/main/java/org/onlab/timer/Timer.java
net/api/src/main/java/org/onlab/onos/net/ConnectPoint.java
View file @
df652ad
...
...
@@ -2,7 +2,7 @@ package org.onlab.onos.net;
import
java.util.Objects
;
import
static
com
.
google
.
common
.
base
.
MoreObjects
.
toStringHelper
;
import
com.google.common.base.MoreObjects
;
/**
* Abstraction of a network connection point expressed as a pair of the
...
...
@@ -42,13 +42,12 @@ public class ConnectPoint {
* @throws java.lang.IllegalStateException if connection point is not
* associated with a device
*/
@SuppressWarnings
(
"unchecked"
)
public
DeviceId
deviceId
()
{
if
(
elementId
instanceof
DeviceId
)
{
return
(
DeviceId
)
elementId
;
}
throw
new
IllegalStateException
(
"Connection point not associated "
+
"with an infrastructure device"
);
"with an infrastructure device"
);
}
/**
...
...
@@ -77,7 +76,7 @@ public class ConnectPoint {
@Override
public
String
toString
()
{
return
toStringHelper
(
this
)
return
MoreObjects
.
toStringHelper
(
this
)
.
add
(
"elementId"
,
elementId
)
.
add
(
"portNumber"
,
portNumber
)
.
toString
();
...
...
net/core/trivial/src/main/java/org/onlab/onos/net/trivial/impl/SimpleLinkManager.java
View file @
df652ad
package
org
.
onlab
.
onos
.
net
.
trivial
.
impl
;
import
com.google.common.collect.Sets
;
import
static
com
.
google
.
common
.
base
.
Preconditions
.
checkNotNull
;
import
static
org
.
slf4j
.
LoggerFactory
.
getLogger
;
import
java.util.Set
;
import
org.apache.felix.scr.annotations.Activate
;
import
org.apache.felix.scr.annotations.Component
;
import
org.apache.felix.scr.annotations.Deactivate
;
...
...
@@ -24,10 +28,7 @@ import org.onlab.onos.net.provider.AbstractProviderRegistry;
import
org.onlab.onos.net.provider.AbstractProviderService
;
import
org.slf4j.Logger
;
import
java.util.Set
;
import
static
com
.
google
.
common
.
base
.
Preconditions
.
checkNotNull
;
import
static
org
.
slf4j
.
LoggerFactory
.
getLogger
;
import
com.google.common.collect.Sets
;
/**
* Provides basic implementation of the link SB & NB APIs.
...
...
@@ -35,8 +36,8 @@ import static org.slf4j.LoggerFactory.getLogger;
@Component
(
immediate
=
true
)
@Service
public
class
SimpleLinkManager
extends
AbstractProviderRegistry
<
LinkProvider
,
LinkProviderService
>
implements
LinkService
,
LinkAdminService
,
LinkProviderRegistry
{
extends
AbstractProviderRegistry
<
LinkProvider
,
LinkProviderService
>
implements
LinkService
,
LinkAdminService
,
LinkProviderRegistry
{
private
static
final
String
DEVICE_ID_NULL
=
"Device ID cannot be null"
;
private
static
final
String
LINK_DESC_NULL
=
"Link description cannot be null"
;
...
...
@@ -45,7 +46,7 @@ public class SimpleLinkManager
private
final
Logger
log
=
getLogger
(
getClass
());
private
final
AbstractListenerRegistry
<
LinkEvent
,
LinkListener
>
listenerRegistry
=
new
AbstractListenerRegistry
<>();
listenerRegistry
=
new
AbstractListenerRegistry
<>();
private
final
SimpleLinkStore
store
=
new
SimpleLinkStore
();
...
...
@@ -83,7 +84,7 @@ public class SimpleLinkManager
public
Set
<
Link
>
getDeviceLinks
(
DeviceId
deviceId
)
{
checkNotNull
(
deviceId
,
DEVICE_ID_NULL
);
return
Sets
.
union
(
store
.
getDeviceEgressLinks
(
deviceId
),
store
.
getDeviceIngressLinks
(
deviceId
));
store
.
getDeviceIngressLinks
(
deviceId
));
}
@Override
...
...
@@ -102,7 +103,7 @@ public class SimpleLinkManager
public
Set
<
Link
>
getLinks
(
ConnectPoint
connectPoint
)
{
checkNotNull
(
connectPoint
,
CONNECT_POINT_NULL
);
return
Sets
.
union
(
store
.
getEgressLinks
(
connectPoint
),
store
.
getIngressLinks
(
connectPoint
));
store
.
getIngressLinks
(
connectPoint
));
}
@Override
...
...
@@ -146,7 +147,7 @@ public class SimpleLinkManager
// Personalized link provider service issued to the supplied provider.
private
class
InternalLinkProviderService
extends
AbstractProviderService
<
LinkProvider
>
implements
LinkProviderService
{
implements
LinkProviderService
{
public
InternalLinkProviderService
(
LinkProvider
provider
)
{
super
(
provider
);
...
...
@@ -156,9 +157,9 @@ public class SimpleLinkManager
public
void
linkDetected
(
LinkDescription
linkDescription
)
{
checkNotNull
(
linkDescription
,
LINK_DESC_NULL
);
checkValidity
();
log
.
info
(
"Link {} detected"
,
linkDescription
);
log
.
debug
(
"Link {} detected"
,
linkDescription
);
LinkEvent
event
=
store
.
createOrUpdateLink
(
provider
().
id
(),
linkDescription
);
linkDescription
);
post
(
event
);
}
...
...
@@ -168,7 +169,7 @@ public class SimpleLinkManager
checkValidity
();
log
.
info
(
"Link {} vanished"
,
linkDescription
);
LinkEvent
event
=
store
.
removeLink
(
linkDescription
.
src
(),
linkDescription
.
dst
());
linkDescription
.
dst
());
post
(
event
);
}
...
...
of/api/src/main/java/org/onlab/onos/of/controller/DefaultPacketContext.java
View file @
df652ad
...
...
@@ -75,4 +75,9 @@ public final class DefaultPacketContext implements PacketContext {
return
new
DefaultPacketContext
(
s
,
pkt
);
}
@Override
public
Integer
inPort
()
{
return
pktin
.
getInPort
().
getPortNumber
();
}
}
...
...
of/api/src/main/java/org/onlab/onos/of/controller/PacketContext.java
View file @
df652ad
...
...
@@ -48,4 +48,10 @@ public interface PacketContext {
* @return the dpid of the switch.
*/
public
Dpid
dpid
();
/**
* Provide the port on which the packet arrived.
* @return the port
*/
public
Integer
inPort
();
}
...
...
of/ctl/src/main/java/org/onlab/onos/of/controller/impl/OFChannelHandler.java
View file @
df652ad
...
...
@@ -415,12 +415,14 @@ class OFChannelHandler extends IdleStateAwareChannelHandler {
OFDescStatsReply
drep
=
(
OFDescStatsReply
)
m
;
// Here is where we differentiate between different kinds of switches
h
.
sw
=
h
.
controller
.
getOFSwitchInstance
(
h
.
thisdpid
,
drep
,
h
.
ofVersion
);
h
.
sw
.
setOFVersion
(
h
.
ofVersion
);
h
.
sw
.
setFeaturesReply
(
h
.
featuresReply
);
h
.
sw
.
setPortDescReply
(
h
.
portDescReply
);
h
.
sw
.
setConnected
(
true
);
h
.
sw
.
setChannel
(
h
.
channel
);
boolean
success
=
h
.
sw
.
connectSwitch
();
if
(!
success
)
{
disconnectDuplicate
(
h
);
return
;
...
...
@@ -432,10 +434,10 @@ class OFChannelHandler extends IdleStateAwareChannelHandler {
log
.
info
(
"Switch {} bound to class {}, description {}"
,
new
Object
[]
{
h
.
sw
,
h
.
sw
.
getClass
(),
drep
});
//Put switch in EQUAL mode until we hear back from the global registry
log
.
debug
(
"Setting new switch {} to EQUAL and sending Role request"
,
h
.
sw
.
getStringId
());
h
.
sw
.
activateEqualSwitch
();
h
.
setSwitchRole
(
RoleState
.
EQUAL
);
//
log.debug("Setting new switch {} to EQUAL and sending Role request",
//
h.sw.getStringId());
//
h.sw.activateEqualSwitch();
//
h.setSwitchRole(RoleState.EQUAL);
h
.
sw
.
startDriverHandshake
();
h
.
setState
(
WAIT_SWITCH_DRIVER_SUB_HANDSHAKE
);
...
...
of/ctl/src/main/java/org/onlab/onos/of/controller/impl/OpenFlowControllerImpl.java
View file @
df652ad
package
org
.
onlab
.
onos
.
of
.
controller
.
impl
;
import
java.util.ArrayList
;
import
java.util.HashSet
;
import
java.util.List
;
import
java.util.Set
;
import
java.util.concurrent.ConcurrentHashMap
;
import
java.util.concurrent.locks.Lock
;
import
java.util.concurrent.locks.ReentrantLock
;
import
org.apache.felix.scr.annotations.Activate
;
import
org.apache.felix.scr.annotations.Component
;
import
org.apache.felix.scr.annotations.Deactivate
;
import
org.apache.felix.scr.annotations.Service
;
import
org.onlab.onos.of.controller.DefaultPacketContext
;
import
org.onlab.onos.of.controller.Dpid
;
import
org.onlab.onos.of.controller.OpenFlowController
;
import
org.onlab.onos.of.controller.OpenFlowSwitch
;
...
...
@@ -12,18 +21,11 @@ import org.onlab.onos.of.controller.PacketListener;
import
org.onlab.onos.of.controller.RoleState
;
import
org.onlab.onos.of.controller.driver.OpenFlowAgent
;
import
org.projectfloodlight.openflow.protocol.OFMessage
;
import
org.projectfloodlight.openflow.protocol.OFPacketIn
;
import
org.projectfloodlight.openflow.protocol.OFPortStatus
;
import
org.slf4j.Logger
;
import
org.slf4j.LoggerFactory
;
import
java.util.ArrayList
;
import
java.util.HashSet
;
import
java.util.List
;
import
java.util.Set
;
import
java.util.concurrent.ConcurrentHashMap
;
import
java.util.concurrent.locks.Lock
;
import
java.util.concurrent.locks.ReentrantLock
;
@Component
(
immediate
=
true
)
@Service
public
class
OpenFlowControllerImpl
implements
OpenFlowController
{
...
...
@@ -42,238 +44,244 @@ public class OpenFlowControllerImpl implements OpenFlowController {
protected
Set
<
OpenFlowSwitchListener
>
ofEventListener
=
new
HashSet
<>();
protected
List
<
PacketListener
>
ofPacketListener
=
new
ArrayList
<>();
private
final
Controller
ctrl
=
new
Controller
();
@Activate
public
void
activate
()
{
ctrl
.
start
(
agent
);
}
@Deactivate
public
void
deactivate
()
{
ctrl
.
stop
();
}
@Override
public
Iterable
<
OpenFlowSwitch
>
getSwitches
()
{
return
connectedSwitches
.
values
();
}
@Override
public
Iterable
<
OpenFlowSwitch
>
getMasterSwitches
()
{
return
activeMasterSwitches
.
values
();
}
@Override
public
Iterable
<
OpenFlowSwitch
>
getEqualSwitches
()
{
return
activeEqualSwitches
.
values
();
}
@Override
public
OpenFlowSwitch
getSwitch
(
Dpid
dpid
)
{
return
connectedSwitches
.
get
(
dpid
);
}
@Override
public
OpenFlowSwitch
getMasterSwitch
(
Dpid
dpid
)
{
return
activeMasterSwitches
.
get
(
dpid
);
}
@Override
public
OpenFlowSwitch
getEqualSwitch
(
Dpid
dpid
)
{
return
activeEqualSwitches
.
get
(
dpid
);
}
@Override
public
void
addListener
(
OpenFlowSwitchListener
listener
)
{
if
(!
ofEventListener
.
contains
(
listener
))
{
this
.
ofEventListener
.
add
(
listener
);
}
}
@Override
public
void
removeListener
(
OpenFlowSwitchListener
listener
)
{
this
.
ofEventListener
.
remove
(
listener
);
}
@Override
public
void
addPacketListener
(
int
priority
,
PacketListener
listener
)
{
ofPacketListener
.
add
(
priority
,
listener
);
}
@Override
public
void
removePacketListener
(
PacketListener
listener
)
{
ofPacketListener
.
remove
(
listener
);
}
@Override
public
void
write
(
Dpid
dpid
,
OFMessage
msg
)
{
this
.
getSwitch
(
dpid
).
sendMsg
(
msg
);
}
@Override
public
void
processPacket
(
Dpid
dpid
,
OFMessage
msg
)
{
switch
(
msg
.
getType
())
{
case
PORT_STATUS:
for
(
OpenFlowSwitchListener
l
:
ofEventListener
)
{
l
.
portChanged
(
dpid
,
(
OFPortStatus
)
msg
);
}
break
;
case
PACKET_IN:
for
(
PacketListener
p
:
ofPacketListener
)
{
//TODO fix me!
p
.
handlePacket
(
null
);
}
break
;
default
:
log
.
warn
(
"Handling message type {} not yet implemented"
,
msg
.
getType
());
}
}
@Override
public
void
setRole
(
Dpid
dpid
,
RoleState
role
)
{
getSwitch
(
dpid
).
setRole
(
role
);
}
/**
* Implementation of an OpenFlow Agent which is responsible for
* keeping track of connected switches and the state in which
* they are.
*/
public
class
OpenFlowSwitchAgent
implements
OpenFlowAgent
{
private
final
Logger
log
=
LoggerFactory
.
getLogger
(
OpenFlowSwitchAgent
.
class
);
private
final
Lock
switchLock
=
new
ReentrantLock
();
@Override
public
boolean
addConnectedSwitch
(
Dpid
dpid
,
OpenFlowSwitch
sw
)
{
if
(
connectedSwitches
.
get
(
dpid
)
!=
null
)
{
log
.
error
(
"Trying to add connectedSwitch but found a previous "
+
"value for dpid: {}"
,
dpid
);
return
false
;
}
else
{
log
.
error
(
"Added switch {}"
,
dpid
);
connectedSwitches
.
put
(
dpid
,
sw
);
for
(
OpenFlowSwitchListener
l
:
ofEventListener
)
{
l
.
switchAdded
(
dpid
);
}
return
true
;
}
}
@Override
public
boolean
validActivation
(
Dpid
dpid
)
{
if
(
connectedSwitches
.
get
(
dpid
)
==
null
)
{
log
.
error
(
"Trying to activate switch but is not in "
+
"connected switches: dpid {}. Aborting .."
,
dpid
);
return
false
;
}
if
(
activeMasterSwitches
.
get
(
dpid
)
!=
null
||
activeEqualSwitches
.
get
(
dpid
)
!=
null
)
{
log
.
error
(
"Trying to activate switch but it is already "
+
"activated: dpid {}. Found in activeMaster: {} "
+
"Found in activeEqual: {}. Aborting .."
,
new
Object
[]{
dpid
,
(
activeMasterSwitches
.
get
(
dpid
)
==
null
)
?
'N'
:
'Y'
,
(
activeEqualSwitches
.
get
(
dpid
)
==
null
)
?
'N'
:
'Y'
});
return
false
;
}
return
true
;
}
@Override
public
boolean
addActivatedMasterSwitch
(
Dpid
dpid
,
OpenFlowSwitch
sw
)
{
switchLock
.
lock
();
try
{
if
(!
validActivation
(
dpid
))
{
return
false
;
}
activeMasterSwitches
.
put
(
dpid
,
sw
);
return
true
;
}
finally
{
switchLock
.
unlock
();
}
}
@Override
public
boolean
addActivatedEqualSwitch
(
Dpid
dpid
,
OpenFlowSwitch
sw
)
{
switchLock
.
lock
();
try
{
if
(!
validActivation
(
dpid
))
{
return
false
;
}
activeEqualSwitches
.
put
(
dpid
,
sw
);
log
.
info
(
"Added Activated EQUAL Switch {}"
,
dpid
);
return
true
;
}
finally
{
switchLock
.
unlock
();
}
}
@Override
public
void
transitionToMasterSwitch
(
Dpid
dpid
)
{
switchLock
.
lock
();
try
{
if
(
activeMasterSwitches
.
containsKey
(
dpid
))
{
return
;
}
OpenFlowSwitch
sw
=
activeEqualSwitches
.
remove
(
dpid
);
if
(
sw
==
null
)
{
log
.
error
(
"Transition to master called on sw {}, but switch "
+
"was not found in controller-cache"
,
dpid
);
return
;
}
log
.
info
(
"Transitioned switch {} to MASTER"
,
dpid
);
activeMasterSwitches
.
put
(
dpid
,
sw
);
}
finally
{
switchLock
.
unlock
();
}
}
@Override
public
void
transitionToEqualSwitch
(
Dpid
dpid
)
{
switchLock
.
lock
();
try
{
if
(
activeEqualSwitches
.
containsKey
(
dpid
))
{
return
;
}
OpenFlowSwitch
sw
=
activeMasterSwitches
.
remove
(
dpid
);
if
(
sw
==
null
)
{
log
.
error
(
"Transition to equal called on sw {}, but switch "
+
"was not found in controller-cache"
,
dpid
);
return
;
}
log
.
info
(
"Transitioned switch {} to EQUAL"
,
dpid
);
activeEqualSwitches
.
put
(
dpid
,
sw
);
}
finally
{
switchLock
.
unlock
();
}
}
@Override
public
void
removeConnectedSwitch
(
Dpid
dpid
)
{
connectedSwitches
.
remove
(
dpid
);
OpenFlowSwitch
sw
=
activeMasterSwitches
.
remove
(
dpid
);
if
(
sw
==
null
)
{
sw
=
activeEqualSwitches
.
remove
(
dpid
);
}
for
(
OpenFlowSwitchListener
l
:
ofEventListener
)
{
l
.
switchRemoved
(
dpid
);
}
}
@Override
public
void
processMessage
(
Dpid
dpid
,
OFMessage
m
)
{
processPacket
(
dpid
,
m
);
}
}
protected
List
<
PacketListener
>
ofPacketListener
=
new
ArrayList
<>();
private
final
Controller
ctrl
=
new
Controller
();
@Activate
public
void
activate
()
{
ctrl
.
start
(
agent
);
}
@Deactivate
public
void
deactivate
()
{
ctrl
.
stop
();
}
@Override
public
Iterable
<
OpenFlowSwitch
>
getSwitches
()
{
return
connectedSwitches
.
values
();
}
@Override
public
Iterable
<
OpenFlowSwitch
>
getMasterSwitches
()
{
return
activeMasterSwitches
.
values
();
}
@Override
public
Iterable
<
OpenFlowSwitch
>
getEqualSwitches
()
{
return
activeEqualSwitches
.
values
();
}
@Override
public
OpenFlowSwitch
getSwitch
(
Dpid
dpid
)
{
return
connectedSwitches
.
get
(
dpid
);
}
@Override
public
OpenFlowSwitch
getMasterSwitch
(
Dpid
dpid
)
{
return
activeMasterSwitches
.
get
(
dpid
);
}
@Override
public
OpenFlowSwitch
getEqualSwitch
(
Dpid
dpid
)
{
return
activeEqualSwitches
.
get
(
dpid
);
}
@Override
public
void
addListener
(
OpenFlowSwitchListener
listener
)
{
if
(!
ofEventListener
.
contains
(
listener
))
{
this
.
ofEventListener
.
add
(
listener
);
}
}
@Override
public
void
removeListener
(
OpenFlowSwitchListener
listener
)
{
this
.
ofEventListener
.
remove
(
listener
);
}
@Override
public
void
addPacketListener
(
int
priority
,
PacketListener
listener
)
{
ofPacketListener
.
add
(
priority
,
listener
);
}
@Override
public
void
removePacketListener
(
PacketListener
listener
)
{
ofPacketListener
.
remove
(
listener
);
}
@Override
public
void
write
(
Dpid
dpid
,
OFMessage
msg
)
{
this
.
getSwitch
(
dpid
).
sendMsg
(
msg
);
}
@Override
public
void
processPacket
(
Dpid
dpid
,
OFMessage
msg
)
{
switch
(
msg
.
getType
())
{
case
PORT_STATUS:
for
(
OpenFlowSwitchListener
l
:
ofEventListener
)
{
l
.
portChanged
(
dpid
,
(
OFPortStatus
)
msg
);
}
break
;
case
PACKET_IN:
for
(
PacketListener
p
:
ofPacketListener
)
{
//TODO fix me!
p
.
handlePacket
(
DefaultPacketContext
.
packetContextFromPacketIn
(
this
.
getSwitch
(
dpid
),
(
OFPacketIn
)
msg
));
}
break
;
default
:
log
.
warn
(
"Handling message type {} not yet implemented {}"
,
msg
.
getType
(),
msg
);
}
}
@Override
public
void
setRole
(
Dpid
dpid
,
RoleState
role
)
{
getSwitch
(
dpid
).
setRole
(
role
);
}
/**
* Implementation of an OpenFlow Agent which is responsible for
* keeping track of connected switches and the state in which
* they are.
*/
public
class
OpenFlowSwitchAgent
implements
OpenFlowAgent
{
private
final
Logger
log
=
LoggerFactory
.
getLogger
(
OpenFlowSwitchAgent
.
class
);
private
final
Lock
switchLock
=
new
ReentrantLock
();
@Override
public
boolean
addConnectedSwitch
(
Dpid
dpid
,
OpenFlowSwitch
sw
)
{
if
(
connectedSwitches
.
get
(
dpid
)
!=
null
)
{
log
.
error
(
"Trying to add connectedSwitch but found a previous "
+
"value for dpid: {}"
,
dpid
);
return
false
;
}
else
{
log
.
error
(
"Added switch {}"
,
dpid
);
connectedSwitches
.
put
(
dpid
,
sw
);
for
(
OpenFlowSwitchListener
l
:
ofEventListener
)
{
l
.
switchAdded
(
dpid
);
}
return
true
;
}
}
@Override
public
boolean
validActivation
(
Dpid
dpid
)
{
if
(
connectedSwitches
.
get
(
dpid
)
==
null
)
{
log
.
error
(
"Trying to activate switch but is not in "
+
"connected switches: dpid {}. Aborting .."
,
dpid
);
return
false
;
}
if
(
activeMasterSwitches
.
get
(
dpid
)
!=
null
||
activeEqualSwitches
.
get
(
dpid
)
!=
null
)
{
log
.
error
(
"Trying to activate switch but it is already "
+
"activated: dpid {}. Found in activeMaster: {} "
+
"Found in activeEqual: {}. Aborting .."
,
new
Object
[]{
dpid
,
(
activeMasterSwitches
.
get
(
dpid
)
==
null
)
?
'N'
:
'Y'
,
(
activeEqualSwitches
.
get
(
dpid
)
==
null
)
?
'N'
:
'Y'
});
return
false
;
}
return
true
;
}
@Override
public
boolean
addActivatedMasterSwitch
(
Dpid
dpid
,
OpenFlowSwitch
sw
)
{
switchLock
.
lock
();
try
{
if
(!
validActivation
(
dpid
))
{
return
false
;
}
activeMasterSwitches
.
put
(
dpid
,
sw
);
return
true
;
}
finally
{
switchLock
.
unlock
();
}
}
@Override
public
boolean
addActivatedEqualSwitch
(
Dpid
dpid
,
OpenFlowSwitch
sw
)
{
switchLock
.
lock
();
try
{
if
(!
validActivation
(
dpid
))
{
return
false
;
}
activeEqualSwitches
.
put
(
dpid
,
sw
);
log
.
info
(
"Added Activated EQUAL Switch {}"
,
dpid
);
return
true
;
}
finally
{
switchLock
.
unlock
();
}
}
@Override
public
void
transitionToMasterSwitch
(
Dpid
dpid
)
{
switchLock
.
lock
();
try
{
if
(
activeMasterSwitches
.
containsKey
(
dpid
))
{
return
;
}
OpenFlowSwitch
sw
=
activeEqualSwitches
.
remove
(
dpid
);
if
(
sw
==
null
)
{
sw
=
getSwitch
(
dpid
);
if
(
sw
==
null
)
{
log
.
error
(
"Transition to master called on sw {}, but switch "
+
"was not found in controller-cache"
,
dpid
);
return
;
}
}
log
.
info
(
"Transitioned switch {} to MASTER"
,
dpid
);
activeMasterSwitches
.
put
(
dpid
,
sw
);
}
finally
{
switchLock
.
unlock
();
}
}
@Override
public
void
transitionToEqualSwitch
(
Dpid
dpid
)
{
switchLock
.
lock
();
try
{
if
(
activeEqualSwitches
.
containsKey
(
dpid
))
{
return
;
}
OpenFlowSwitch
sw
=
activeMasterSwitches
.
remove
(
dpid
);
if
(
sw
==
null
)
{
log
.
error
(
"Transition to equal called on sw {}, but switch "
+
"was not found in controller-cache"
,
dpid
);
return
;
}
log
.
info
(
"Transitioned switch {} to EQUAL"
,
dpid
);
activeEqualSwitches
.
put
(
dpid
,
sw
);
}
finally
{
switchLock
.
unlock
();
}
}
@Override
public
void
removeConnectedSwitch
(
Dpid
dpid
)
{
connectedSwitches
.
remove
(
dpid
);
OpenFlowSwitch
sw
=
activeMasterSwitches
.
remove
(
dpid
);
if
(
sw
==
null
)
{
sw
=
activeEqualSwitches
.
remove
(
dpid
);
}
for
(
OpenFlowSwitchListener
l
:
ofEventListener
)
{
l
.
switchRemoved
(
dpid
);
}
}
@Override
public
void
processMessage
(
Dpid
dpid
,
OFMessage
m
)
{
processPacket
(
dpid
,
m
);
}
}
}
...
...
of/ctl/src/main/java/org/onlab/onos/of/controller/impl/RoleManager.java
View file @
df652ad
...
...
@@ -84,7 +84,7 @@ class RoleManager implements RoleHandler {
default
:
// ensuring that the only two roles sent to 1.0 switches with
// Nicira role support, are MASTER and SLAVE
roleToSend
=
OFNiciraControllerRole
.
ROLE_
SLAVE
;
roleToSend
=
OFNiciraControllerRole
.
ROLE_
OTHER
;
log
.
warn
(
"Sending Nx Role.SLAVE to switch {}."
,
sw
);
}
int
xid
=
sw
.
getNextTransactionId
();
...
...
of/ctl/src/main/java/org/onlab/onos/of/drivers/impl/OFSwitchImplOVS10.java
View file @
df652ad
...
...
@@ -50,8 +50,7 @@ public class OFSwitchImplOVS10 extends AbstractOpenFlowSwitch {
@Override
public
void
write
(
OFMessage
msg
)
{
channel
.
write
(
msg
);
channel
.
write
(
Collections
.
singletonList
(
msg
));
}
@Override
...
...
pom.xml
View file @
df652ad
...
...
@@ -61,6 +61,14 @@
<version>
18.0
</version>
</dependency>
<dependency>
<groupId>
io.netty
</groupId>
<artifactId>
netty
</artifactId>
<version>
3.9.0.Final
</version>
</dependency>
<dependency>
<groupId>
com.google.guava
</groupId>
<artifactId>
guava-testlib
</artifactId>
...
...
providers/of/link/src/main/java/org/onlab/onos/provider/of/link/impl/LinkDiscovery.java
0 → 100644
View file @
df652ad
/*******************************************************************************
* Copyright 2014 Open Networking Laboratory
*
* 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.
******************************************************************************/
package
org
.
onlab
.
onos
.
provider
.
of
.
link
.
impl
;
import
static
org
.
slf4j
.
LoggerFactory
.
getLogger
;
import
java.util.Collections
;
import
java.util.HashMap
;
import
java.util.HashSet
;
import
java.util.Iterator
;
import
java.util.List
;
import
java.util.Map
;
import
java.util.Set
;
import
java.util.concurrent.TimeUnit
;
import
java.util.concurrent.atomic.AtomicInteger
;
import
org.jboss.netty.util.Timeout
;
import
org.jboss.netty.util.TimerTask
;
import
org.onlab.onos.net.ConnectPoint
;
import
org.onlab.onos.net.DeviceId
;
import
org.onlab.onos.net.Link.Type
;
import
org.onlab.onos.net.PortNumber
;
import
org.onlab.onos.net.link.DefaultLinkDescription
;
import
org.onlab.onos.net.link.LinkDescription
;
import
org.onlab.onos.net.link.LinkProviderService
;
import
org.onlab.onos.of.controller.Dpid
;
import
org.onlab.onos.of.controller.OpenFlowController
;
import
org.onlab.onos.of.controller.OpenFlowSwitch
;
import
org.onlab.packet.Ethernet
;
import
org.onlab.packet.ONLabLddp
;
import
org.onlab.packet.ONLabLddp.DPIDandPort
;
import
org.onlab.timer.Timer
;
import
org.projectfloodlight.openflow.protocol.OFFactory
;
import
org.projectfloodlight.openflow.protocol.OFMessage
;
import
org.projectfloodlight.openflow.protocol.OFPacketOut
;
import
org.projectfloodlight.openflow.protocol.OFPortDesc
;
import
org.projectfloodlight.openflow.protocol.action.OFAction
;
import
org.projectfloodlight.openflow.protocol.action.OFActionOutput
;
import
org.projectfloodlight.openflow.types.OFBufferId
;
import
org.projectfloodlight.openflow.types.OFPort
;
import
org.slf4j.Logger
;
/**
* Run discovery process from a physical switch. Ports are initially labeled as
* slow ports. When an LLDP is successfully received, label the remote port as
* fast. Every probeRate milliseconds, loop over all fast ports and send an
* LLDP, send an LLDP for a single slow port. Based on FlowVisor topology
* discovery implementation.
*
* TODO: add 'fast discovery' mode: drop LLDPs in destination switch but listen
* for flow_removed messages
*/
public
class
LinkDiscovery
implements
TimerTask
{
private
final
OpenFlowSwitch
sw
;
// send 1 probe every probeRate milliseconds
private
final
long
probeRate
;
private
final
Set
<
Integer
>
slowPorts
;
private
final
Set
<
Integer
>
fastPorts
;
// number of unacknowledged probes per port
private
final
Map
<
Integer
,
AtomicInteger
>
portProbeCount
;
// number of probes to send before link is removed
private
static
final
short
MAX_PROBE_COUNT
=
3
;
private
Iterator
<
Integer
>
slowIterator
;
private
final
OFFactory
ofFactory
;
private
final
Logger
log
=
getLogger
(
getClass
());
private
final
ONLabLddp
lldpPacket
;
private
final
Ethernet
ethPacket
;
private
Ethernet
bddpEth
;
private
final
boolean
useBDDP
;
private
final
OpenFlowController
ctrl
;
private
final
LinkProviderService
linkProvider
;
/**
* Instantiates discovery manager for the given physical switch. Creates a
* generic LLDP packet that will be customized for the port it is sent out on.
* Starts the the timer for the discovery process.
*
* @param sw the physical switch
* @param useBDDP flag to also use BDDP for discovery
*/
public
LinkDiscovery
(
final
OpenFlowSwitch
sw
,
OpenFlowController
ctrl
,
LinkProviderService
providerService
,
Boolean
...
useBDDP
)
{
this
.
sw
=
sw
;
this
.
ofFactory
=
sw
.
factory
();
this
.
ctrl
=
ctrl
;
this
.
probeRate
=
1000
;
this
.
linkProvider
=
providerService
;
this
.
slowPorts
=
Collections
.
synchronizedSet
(
new
HashSet
<
Integer
>());
this
.
fastPorts
=
Collections
.
synchronizedSet
(
new
HashSet
<
Integer
>());
this
.
portProbeCount
=
new
HashMap
<
Integer
,
AtomicInteger
>();
this
.
lldpPacket
=
new
ONLabLddp
();
this
.
lldpPacket
.
setSwitch
(
this
.
sw
.
getId
());
this
.
ethPacket
=
new
Ethernet
();
this
.
ethPacket
.
setEtherType
(
Ethernet
.
TYPE_LLDP
);
this
.
ethPacket
.
setDestinationMACAddress
(
ONLabLddp
.
LLDP_NICIRA
);
this
.
ethPacket
.
setPayload
(
this
.
lldpPacket
);
this
.
ethPacket
.
setPad
(
true
);
this
.
useBDDP
=
useBDDP
.
length
>
0
?
useBDDP
[
0
]
:
false
;
if
(
this
.
useBDDP
)
{
this
.
bddpEth
=
new
Ethernet
();
this
.
bddpEth
.
setPayload
(
this
.
lldpPacket
);
this
.
bddpEth
.
setEtherType
(
Ethernet
.
TYPE_BSN
);
this
.
bddpEth
.
setDestinationMACAddress
(
ONLabLddp
.
BDDP_MULTICAST
);
this
.
bddpEth
.
setPad
(
true
);
log
.
info
(
"Using BDDP to discover network"
);
}
for
(
OFPortDesc
port
:
sw
.
getPorts
())
{
if
(
port
.
getPortNo
()
!=
OFPort
.
LOCAL
)
{
addPort
(
port
);
}
}
Timer
.
getTimer
().
newTimeout
(
this
,
this
.
probeRate
,
TimeUnit
.
MILLISECONDS
);
this
.
log
.
debug
(
"Started discovery manager for switch {}"
,
sw
.
getId
());
}
/**
* Add physical port port to discovery process.
* Send out initial LLDP and label it as slow port.
*
* @param port the port
*/
public
void
addPort
(
final
OFPortDesc
port
)
{
// Ignore ports that are not on this switch, or already booted. */
synchronized
(
this
)
{
this
.
log
.
debug
(
"sending init probe to port {}"
,
port
.
getPortNo
().
getPortNumber
());
OFPacketOut
pkt
;
pkt
=
this
.
createLLDPPacketOut
(
port
);
this
.
sw
.
sendMsg
(
pkt
);
if
(
useBDDP
)
{
OFPacketOut
bpkt
=
this
.
createBDDPPacketOut
(
port
);
this
.
sw
.
sendMsg
(
bpkt
);
}
this
.
slowPorts
.
add
(
port
.
getPortNo
().
getPortNumber
());
this
.
slowIterator
=
this
.
slowPorts
.
iterator
();
}
}
/**
* Removes physical port from discovery process.
*
* @param port the port
*/
public
void
removePort
(
final
OFPort
port
)
{
// Ignore ports that are not on this switch
int
portnum
=
port
.
getPortNumber
();
synchronized
(
this
)
{
if
(
this
.
slowPorts
.
contains
(
portnum
))
{
this
.
slowPorts
.
remove
(
portnum
);
this
.
slowIterator
=
this
.
slowPorts
.
iterator
();
}
else
if
(
this
.
fastPorts
.
contains
(
portnum
))
{
this
.
fastPorts
.
remove
(
portnum
);
this
.
portProbeCount
.
remove
(
portnum
);
// no iterator to update
}
else
{
this
.
log
.
warn
(
"tried to dynamically remove non-existing port {}"
,
portnum
);
}
}
}
/**
* Method called by remote port to acknowledge receipt of LLDP sent by
* this port. If slow port, updates label to fast. If fast port, decrements
* number of unacknowledged probes.
*
* @param port the port
*/
public
void
ackProbe
(
final
Integer
port
)
{
final
int
portNumber
=
port
;
synchronized
(
this
)
{
if
(
this
.
slowPorts
.
contains
(
portNumber
))
{
this
.
log
.
debug
(
"Setting slow port to fast: {}:{}"
,
this
.
sw
.
getId
(),
portNumber
);
this
.
slowPorts
.
remove
(
portNumber
);
this
.
slowIterator
=
this
.
slowPorts
.
iterator
();
this
.
fastPorts
.
add
(
portNumber
);
this
.
portProbeCount
.
put
(
portNumber
,
new
AtomicInteger
(
0
));
}
else
{
if
(
this
.
fastPorts
.
contains
(
portNumber
))
{
this
.
portProbeCount
.
get
(
portNumber
).
set
(
0
);
}
else
{
this
.
log
.
debug
(
"Got ackProbe for non-existing port: {}"
,
portNumber
);
}
}
}
}
/**
* Creates packet_out LLDP for specified output port.
*
* @param port the port
* @return Packet_out message with LLDP data
* @throws PortMappingException
*/
private
OFPacketOut
createLLDPPacketOut
(
final
OFPortDesc
port
)
{
OFPacketOut
.
Builder
packetOut
=
this
.
ofFactory
.
buildPacketOut
();
packetOut
.
setBufferId
(
OFBufferId
.
NO_BUFFER
);
OFAction
act
=
this
.
ofFactory
.
actions
().
buildOutput
()
.
setPort
(
port
.
getPortNo
()).
build
();
packetOut
.
setActions
(
Collections
.
singletonList
(
act
));
this
.
lldpPacket
.
setPort
(
port
.
getPortNo
().
getPortNumber
());
this
.
ethPacket
.
setSourceMACAddress
(
port
.
getHwAddr
().
getBytes
());
final
byte
[]
lldp
=
this
.
ethPacket
.
serialize
();
packetOut
.
setData
(
lldp
);
return
packetOut
.
build
();
}
/**
* Creates packet_out BDDP for specified output port.
*
* @param port the port
* @return Packet_out message with LLDP data
* @throws PortMappingException
*/
private
OFPacketOut
createBDDPPacketOut
(
final
OFPortDesc
port
)
{
OFPacketOut
.
Builder
packetOut
=
sw
.
factory
().
buildPacketOut
();
packetOut
.
setBufferId
(
OFBufferId
.
NO_BUFFER
);
OFActionOutput
.
Builder
act
=
sw
.
factory
().
actions
().
buildOutput
()
.
setPort
(
port
.
getPortNo
());
OFAction
out
=
act
.
build
();
packetOut
.
setActions
(
Collections
.
singletonList
(
out
));
this
.
lldpPacket
.
setPort
(
port
.
getPortNo
().
getPortNumber
());
this
.
bddpEth
.
setSourceMACAddress
(
port
.
getHwAddr
().
getBytes
());
final
byte
[]
bddp
=
this
.
bddpEth
.
serialize
();
packetOut
.
setData
(
bddp
);
return
packetOut
.
build
();
}
private
void
sendMsg
(
final
OFMessage
msg
)
{
this
.
sw
.
sendMsg
(
msg
);
}
public
String
getName
()
{
return
"LinkDiscovery "
+
this
.
sw
.
getStringId
();
}
/*
* Handles an incoming LLDP packet. Creates link in topology and sends ACK
* to port where LLDP originated.
*/
@SuppressWarnings
(
"rawtypes"
)
public
void
handleLLDP
(
final
Ethernet
eth
,
Integer
inPort
)
{
final
byte
[]
pkt
=
eth
.
serialize
();
if
(
ONLabLddp
.
isOVXLLDP
(
pkt
))
{
final
Integer
dstPort
=
inPort
;
final
DPIDandPort
dp
=
ONLabLddp
.
parseLLDP
(
pkt
);
final
OpenFlowSwitch
srcSwitch
=
ctrl
.
getSwitch
(
new
Dpid
(
dp
.
getDpid
()));
final
Integer
srcPort
=
dp
.
getPort
();
if
(
srcSwitch
==
null
)
{
return
;
}
this
.
ackProbe
(
srcPort
);
ConnectPoint
src
=
new
ConnectPoint
(
DeviceId
.
deviceId
(
"of:"
+
Long
.
toHexString
(
srcSwitch
.
getId
())),
PortNumber
.
portNumber
(
srcPort
));
ConnectPoint
dst
=
new
ConnectPoint
(
DeviceId
.
deviceId
(
"of:"
+
Long
.
toHexString
(
sw
.
getId
())),
PortNumber
.
portNumber
(
dstPort
));
LinkDescription
ld
;
if
(
eth
.
getEtherType
()
==
Ethernet
.
TYPE_BSN
)
{
ld
=
new
DefaultLinkDescription
(
src
,
dst
,
Type
.
INDIRECT
);
}
else
{
ld
=
new
DefaultLinkDescription
(
src
,
dst
,
Type
.
DIRECT
);
}
linkProvider
.
linkDetected
(
ld
);
}
else
{
this
.
log
.
debug
(
"Ignoring unknown LLDP"
);
}
}
private
OFPortDesc
findPort
(
List
<
OFPortDesc
>
ports
,
Integer
inPort
)
{
for
(
OFPortDesc
p
:
ports
)
{
if
(
p
.
getPortNo
().
getPortNumber
()
==
inPort
)
{
return
p
;
}
}
return
null
;
}
/**
* Execute this method every t milliseconds. Loops over all ports
* labeled as fast and sends out an LLDP. Send out an LLDP on a single slow
* port.
*
* @param t timeout
* @throws Exception
*/
@Override
public
void
run
(
final
Timeout
t
)
{
this
.
log
.
debug
(
"sending probes"
);
synchronized
(
this
)
{
final
Iterator
<
Integer
>
fastIterator
=
this
.
fastPorts
.
iterator
();
while
(
fastIterator
.
hasNext
())
{
final
Integer
portNumber
=
fastIterator
.
next
();
final
int
probeCount
=
this
.
portProbeCount
.
get
(
portNumber
)
.
getAndIncrement
();
OFPortDesc
port
=
findPort
(
this
.
sw
.
getPorts
(),
portNumber
);
if
(
probeCount
<
LinkDiscovery
.
MAX_PROBE_COUNT
)
{
this
.
log
.
debug
(
"sending fast probe to port"
);
OFPacketOut
pkt
=
this
.
createLLDPPacketOut
(
port
);
this
.
sendMsg
(
pkt
);
if
(
useBDDP
)
{
OFPacketOut
bpkt
=
this
.
createBDDPPacketOut
(
port
);
this
.
sendMsg
(
bpkt
);
}
}
else
{
// Update fast and slow ports
fastIterator
.
remove
();
this
.
slowPorts
.
add
(
portNumber
);
this
.
slowIterator
=
this
.
slowPorts
.
iterator
();
this
.
portProbeCount
.
remove
(
portNumber
);
// Remove link from topology
final
OFPortDesc
srcPort
=
port
;
ConnectPoint
cp
=
new
ConnectPoint
(
DeviceId
.
deviceId
(
"of:"
+
Long
.
toHexString
(
sw
.
getId
())),
PortNumber
.
portNumber
(
srcPort
.
getPortNo
().
getPortNumber
()));
linkProvider
.
linksVanished
(
cp
);
}
}
// send a probe for the next slow port
if
(
this
.
slowPorts
.
size
()
>
0
)
{
if
(!
this
.
slowIterator
.
hasNext
())
{
this
.
slowIterator
=
this
.
slowPorts
.
iterator
();
}
if
(
this
.
slowIterator
.
hasNext
())
{
final
int
portNumber
=
this
.
slowIterator
.
next
();
this
.
log
.
debug
(
"sending slow probe to port {}"
,
portNumber
);
OFPortDesc
port
=
findPort
(
this
.
sw
.
getPorts
(),
portNumber
);
OFPacketOut
pkt
=
this
.
createLLDPPacketOut
(
port
);
this
.
sendMsg
(
pkt
);
if
(
useBDDP
)
{
OFPacketOut
bpkt
=
this
.
createBDDPPacketOut
(
port
);
this
.
sendMsg
(
bpkt
);
}
}
}
}
// reschedule timer
Timer
.
getTimer
().
newTimeout
(
this
,
this
.
probeRate
,
TimeUnit
.
MILLISECONDS
);
}
public
void
removeAllPorts
()
{
for
(
OFPortDesc
port
:
sw
.
getPorts
())
{
removePort
(
port
.
getPortNo
());
}
}
}
providers/of/link/src/main/java/org/onlab/onos/provider/of/link/impl/OpenFlowLinkProvider.java
View file @
df652ad
...
...
@@ -2,11 +2,17 @@ package org.onlab.onos.provider.of.link.impl;
import
static
org
.
slf4j
.
LoggerFactory
.
getLogger
;
import
java.util.Map
;
import
java.util.concurrent.ConcurrentHashMap
;
import
org.apache.felix.scr.annotations.Activate
;
import
org.apache.felix.scr.annotations.Component
;
import
org.apache.felix.scr.annotations.Deactivate
;
import
org.apache.felix.scr.annotations.Reference
;
import
org.apache.felix.scr.annotations.ReferenceCardinality
;
import
org.onlab.onos.net.ConnectPoint
;
import
org.onlab.onos.net.DeviceId
;
import
org.onlab.onos.net.PortNumber
;
import
org.onlab.onos.net.link.LinkProvider
;
import
org.onlab.onos.net.link.LinkProviderRegistry
;
import
org.onlab.onos.net.link.LinkProviderService
;
...
...
@@ -17,6 +23,10 @@ import org.onlab.onos.of.controller.OpenFlowController;
import
org.onlab.onos.of.controller.OpenFlowSwitchListener
;
import
org.onlab.onos.of.controller.PacketContext
;
import
org.onlab.onos.of.controller.PacketListener
;
import
org.onlab.timer.Timer
;
import
org.projectfloodlight.openflow.protocol.OFPortConfig
;
import
org.projectfloodlight.openflow.protocol.OFPortDesc
;
import
org.projectfloodlight.openflow.protocol.OFPortState
;
import
org.projectfloodlight.openflow.protocol.OFPortStatus
;
import
org.slf4j.Logger
;
...
...
@@ -37,6 +47,8 @@ public class OpenFlowLinkProvider extends AbstractProvider implements LinkProvid
private
LinkProviderService
providerService
;
private
final
boolean
useBDDP
=
true
;
private
final
InternalLinkProvider
listener
=
new
InternalLinkProvider
();
/**
...
...
@@ -60,32 +72,61 @@ public class OpenFlowLinkProvider extends AbstractProvider implements LinkProvid
controller
.
removeListener
(
listener
);
controller
.
removePacketListener
(
listener
);
providerService
=
null
;
Timer
.
getTimer
().
stop
();
log
.
info
(
"Stopped"
);
}
private
class
InternalLinkProvider
implements
PacketListener
,
OpenFlowSwitchListener
{
private
final
Map
<
Dpid
,
LinkDiscovery
>
discoverers
=
new
ConcurrentHashMap
<>();
@Override
public
void
handlePacket
(
PacketContext
pktCtx
)
{
LinkDiscovery
ld
=
discoverers
.
get
(
pktCtx
.
dpid
());
if
(
ld
==
null
)
{
return
;
}
ld
.
handleLLDP
(
pktCtx
.
parsed
(),
pktCtx
.
inPort
());
}
@Override
public
void
switchAdded
(
Dpid
dpid
)
{
// TODO Auto-generated method stub
discoverers
.
put
(
dpid
,
new
LinkDiscovery
(
controller
.
getSwitch
(
dpid
),
controller
,
providerService
,
useBDDP
));
}
@Override
public
void
switchRemoved
(
Dpid
dpid
)
{
// TODO Auto-generated method stub
LinkDiscovery
ld
=
this
.
discoverers
.
remove
(
dpid
);
if
(
ld
!=
null
)
{
ld
.
removeAllPorts
();
}
providerService
.
linksVanished
(
DeviceId
.
deviceId
(
"of:"
+
Long
.
toHexString
(
dpid
.
value
())));
}
@Override
public
void
portChanged
(
Dpid
dpid
,
OFPortStatus
status
)
{
// TODO Auto-generated method stub
LinkDiscovery
ld
=
discoverers
.
get
(
dpid
);
if
(
ld
==
null
)
{
return
;
}
final
OFPortDesc
port
=
status
.
getDesc
();
final
boolean
enabled
=
!
port
.
getState
().
contains
(
OFPortState
.
LINK_DOWN
)
&&
!
port
.
getConfig
().
contains
(
OFPortConfig
.
PORT_DOWN
);
if
(
enabled
)
{
ld
.
addPort
(
port
);
}
else
{
ConnectPoint
cp
=
new
ConnectPoint
(
DeviceId
.
deviceId
(
"of:"
+
Long
.
toHexString
(
dpid
.
value
())),
PortNumber
.
portNumber
(
port
.
getPortNo
().
getPortNumber
()));
providerService
.
linksVanished
(
cp
);
ld
.
removePort
(
port
.
getPortNo
());
}
}
...
...
utils/misc/pom.xml
View file @
df652ad
...
...
@@ -25,7 +25,10 @@
<dependency>
<groupId>
io.netty
</groupId>
<artifactId>
netty
</artifactId>
<version>
3.9.0.Final
</version>
</dependency>
<dependency>
<groupId>
commons-lang
</groupId>
<artifactId>
commons-lang
</artifactId>
</dependency>
</dependencies>
...
...
utils/misc/src/main/java/org/onlab/packet/ONLabLddp.java
View file @
df652ad
...
...
@@ -21,6 +21,8 @@ import java.util.LinkedList;
import
java.util.List
;
import
org.apache.commons.lang.ArrayUtils
;
import
org.slf4j.Logger
;
import
org.slf4j.LoggerFactory
;
/**
...
...
@@ -31,6 +33,7 @@ import org.apache.commons.lang.ArrayUtils;
@SuppressWarnings
(
"rawtypes"
)
public
class
ONLabLddp
extends
LLDP
{
private
static
final
Logger
log
=
LoggerFactory
.
getLogger
(
ONLabLddp
.
class
);
// ON.Lab OUI and OVX name for organizationally specific TLVs
public
static
final
byte
[]
ONLAB_OUI
=
{(
byte
)
0xa4
,
0x23
,
0x05
};
public
static
final
String
OVX_NAME
=
"OpenVirteX"
;
...
...
@@ -50,7 +53,7 @@ public class ONLabLddp extends LLDP {
private
static
final
byte
CHASSIS_TLV_SUBTYPE
=
4
;
private
static
final
byte
PORT_TLV_TYPE
=
2
;
private
static
final
byte
PORT_TLV_SIZE
=
7
;
private
static
final
byte
PORT_TLV_SIZE
=
5
;
private
static
final
byte
PORT_TLV_SUBTYPE
=
2
;
private
static
final
byte
TTL_TLV_TYPE
=
3
;
...
...
@@ -60,7 +63,7 @@ public class ONLabLddp extends LLDP {
// 4 = OUI (3) + subtype (1)
private
static
final
byte
NAME_TLV_SIZE
=
(
byte
)
(
4
+
ONLabLddp
.
OVX_NAME
.
length
());
private
static
final
byte
NAME_TLV_SUBTYPE
=
1
;
private
static
final
short
NAME_TLV_OFFSET
=
3
2
;
private
static
final
short
NAME_TLV_OFFSET
=
3
4
;
private
static
final
short
NAME_TLV_HEADER
=
(
short
)
((
NAME_TLV_TYPE
<<
9
)
|
NAME_TLV_SIZE
);
// Contents of full name TLV
private
static
final
byte
[]
NAME_TLV
=
ByteBuffer
.
allocate
(
NAME_TLV_SIZE
+
2
)
...
...
@@ -85,7 +88,7 @@ public class ONLabLddp extends LLDP {
// Default switch, port number and TTL
private
static
final
byte
[]
DEFAULT_DPID
=
{
0x00
,
0x00
,
0x00
,
0x00
,
0x00
,
0x00
,
0x00
,
0x00
};
private
static
final
shor
t
DEFAULT_PORT
=
0
;
private
static
final
in
t
DEFAULT_PORT
=
0
;
private
static
final
short
DEFAULT_TTL
=
120
;
// in seconds
// Minimum and OVX-generated LLDP packet sizes
...
...
@@ -97,7 +100,7 @@ public class ONLabLddp extends LLDP {
// Field offsets in OVX-generated LLDP
private
static
final
short
ETHERTYPE_OFFSET
=
12
;
private
static
final
short
PORT_OFFSET
=
26
;
private
static
final
short
DPID_OFFSET
=
5
4
;
private
static
final
short
DPID_OFFSET
=
5
6
;
// Private member fields
// Byte arrays for TLV information string
...
...
@@ -167,10 +170,10 @@ public class ONLabLddp extends LLDP {
*
* @param portNumber the port number
*/
private
void
setPortTLV
(
final
long
portNumber
)
{
private
void
setPortTLV
(
final
int
portNumber
)
{
this
.
bb
=
ByteBuffer
.
wrap
(
this
.
portId
);
this
.
bb
.
put
(
PORT_TLV_SUBTYPE
);
this
.
bb
.
put
Long
(
portNumber
);
this
.
bb
.
put
Int
(
portNumber
);
this
.
portTLV
.
setLength
(
PORT_TLV_SIZE
);
this
.
portTLV
.
setType
(
PORT_TLV_TYPE
);
...
...
@@ -240,8 +243,8 @@ public class ONLabLddp extends LLDP {
*
* @param port the port instance
*/
public
void
setPort
(
long
port
)
{
long
portNumber
=
port
;
public
void
setPort
(
int
port
)
{
int
portNumber
=
port
;
this
.
setPortTLV
(
portNumber
);
}
...
...
@@ -335,7 +338,7 @@ public class ONLabLddp extends LLDP {
* @param packet
* @return Dpid and port
*/
/* public static long
parseLLDP(final byte[] packet) {
public
static
DPIDandPort
parseLLDP
(
final
byte
[]
packet
)
{
final
ByteBuffer
bb
=
ByteBuffer
.
wrap
(
packet
);
// Extra offset due to VLAN tag
...
...
@@ -345,10 +348,30 @@ public class ONLabLddp extends LLDP {
offset
=
4
;
}
final
short port = bb.getLong
(PORT_OFFSET + offset);
final
int
port
=
bb
.
getInt
(
PORT_OFFSET
+
offset
);
final
long
dpid
=
bb
.
getLong
(
DPID_OFFSET
+
offset
);
return
dpid
return
new
DPIDandPort
(
dpid
,
port
);
}
*/
public
static
class
DPIDandPort
{
private
final
long
dpid
;
private
final
int
port
;
public
DPIDandPort
(
long
dpid
,
int
port
)
{
this
.
dpid
=
dpid
;
this
.
port
=
port
;
}
public
long
getDpid
()
{
return
this
.
dpid
;
}
public
int
getPort
()
{
return
this
.
port
;
}
}
}
...
...
utils/misc/src/main/java/org/onlab/timer/Timer.java
0 → 100644
View file @
df652ad
package
org
.
onlab
.
timer
;
import
org.jboss.netty.util.HashedWheelTimer
;
public
final
class
Timer
{
private
Timer
()
{}
private
static
HashedWheelTimer
timer
;
public
static
HashedWheelTimer
getTimer
()
{
if
(
Timer
.
timer
==
null
)
{
Timer
.
timer
=
new
HashedWheelTimer
();
Timer
.
timer
.
start
();
}
return
Timer
.
timer
;
}
}
Please
register
or
login
to post a comment