Index: source/ariba/utility/types/LinkID.cpp
===================================================================
--- source/ariba/utility/types/LinkID.cpp	(revision 7744)
+++ source/ariba/utility/types/LinkID.cpp	(revision 9684)
@@ -39,35 +39,51 @@
 #include "LinkID.h"
 
+#include <boost/unordered_map.hpp>
+
 namespace ariba {
 namespace utility {
 
-const LinkID LinkID::UNSPECIFIED; // for this link isvalid is always false!
+/// the unspecified link id
+const LinkID LinkID::UNSPECIFIED;
 
-LinkID::LinkID() : isvalid(false) {
+const char* UNSPECIFIED_LINK 	= "<LINKID-UNSPECIFIED>";
+const char* UNKNOWN_LINK 		= "<LINKID-UNKNOWN>";
+const char* NULL_INFO 			= "<NO-INFO-AVAILABLE>";
+
+boost::unordered_map<uint16_t, const char*> link_ids;
+
+bool LinkID::isValid( const LinkID& id ) {
+	return link_ids.count(id.local_id)!=0;
 }
 
-LinkID::LinkID(const Identifier& identifier) : Identifier(identifier), isvalid(true) {
+const char* LinkID::getInfo( const LinkID& id ) {
+	if (!id.valid())
+		return UNSPECIFIED_LINK;
+	if ( link_ids.count(id.local_id) == 0 )
+		return UNKNOWN_LINK;
+	const char* info = link_ids.find( id.local_id )->second;
+	if (info == NULL)
+		return NULL_INFO;
+	return info;
 }
 
-LinkID::~LinkID() {
+/// create a new locally unique link id
+LinkID LinkID::create( const char* info ) {
+	assert( link_ids.size() != 0xFFFE );
+	uint16_t id;
+	do {
+		id = rand() & 0xFFFF;
+	} while (id == 0 || link_ids.count(id) != 0);
+	link_ids.insert( std::make_pair(id, info) );
+	return LinkID(id);
 }
 
-LinkID::LinkID(const LinkID& rh) : Identifier(rh) {
+/// free a locally unique link id
+void LinkID::destroy( const LinkID& id ) {
+	link_ids.erase(id.local_id);
 }
 
-LinkID& LinkID::operator=(const LinkID& rh){
-
-	Identifier::operator=( rh );
-	this->isvalid = rh.isvalid;
-
-	return *this;
-}
-
-bool LinkID::valid(){
-	return isvalid;
-}
-
-LinkID LinkID::create() {
-	return LinkID( Identifier::random() );
+std::ostream& operator<<(std::ostream& s, const LinkID& id ) {
+	return s << id.toString();
 }
 
Index: source/ariba/utility/types/LinkID.h
===================================================================
--- source/ariba/utility/types/LinkID.h	(revision 7744)
+++ source/ariba/utility/types/LinkID.h	(revision 9684)
@@ -40,9 +40,14 @@
 #define LINKID_H_
 
+#include <stdlib.h>
+#include <stdint.h>
+#include <stdio.h>
+
 #include <vector>
-#include "ariba/utility/types/Identifier.h"
+#include <string>
+
+#include "ariba/utility/serialization.h"
 
 using std::vector;
-using ariba::utility::Identifier;
 
 namespace ariba {
@@ -50,26 +55,190 @@
 
 /**
- * Represents a link from the base communication.
+ * The link id identifies a link between two devices/nodes.
+ *
+ * Its a 32-bit value, that is composed out of two 16-bit values
+ * identifing a initiator and acceptor id.
  */
-class LinkID : public Identifier {
+class LinkID {
+private:
+	uint16_t local_id;
+	uint16_t initiator_id;
+	uint16_t acceptor_id;
+
+
+	LinkID(uint16_t local_id) {
+		this->local_id = local_id;
+		this->initiator_id = 0;
+		this->acceptor_id = 0;
+	}
+
+	/// returns the full id
+	inline uint32_t getFullId() const {
+		return (initiator_id << 16) + acceptor_id;
+	}
+
+	inline int compareTo( const LinkID& rhs ) const {
+		// compare local id
+		if (rhs.isLocal() && this->isLocal())
+			return local_id - rhs.local_id;
+
+		// compare initiator id
+		else if ((initiator_id == 0 || rhs.initiator_id == 0)
+				&& (acceptor_id == rhs.acceptor_id) ) return 0;
+
+		// compare acceptor id
+		else if ((acceptor_id == 0 || rhs.acceptor_id == 0)
+				&& (initiator_id == rhs.initiator_id) ) return 0;
+
+		// compare full id
+		else if (getFullId() == rhs.getFullId()) return 0;
+		else if (getFullId() <  rhs.getFullId()) return -1;
+		else if (getFullId() >  rhs.getFullId()) return 1;
+		return -1;
+	}
+
+	static const char* getInfo( const LinkID& id );
+
+	static bool isValid( const LinkID& id );
+
 public:
+	/// the unspecified link id
 	static const LinkID UNSPECIFIED;
 
-	LinkID();
-	LinkID(const LinkID& rh);
-	LinkID(const Identifier& identifier);
-	virtual ~LinkID();
-	LinkID& operator=(const LinkID& rh);
-
-	bool valid();
-	static LinkID create();
-
-private:
-	bool isvalid;
+	/// create a new locally unique link id
+	static LinkID create( const char* info = NULL );
+
+	/// free a locally unique link id
+	static void destroy( const LinkID& id );
+
+	/// construct a unspecified id
+	LinkID() {
+		local_id = 0;
+		initiator_id = 0;
+		acceptor_id = 0;
+	}
+
+	/// copy constructor
+	LinkID( const LinkID& rh );
+
+	/// assigns another link id
+	LinkID& operator=(const LinkID& rh) {
+		local_id = rh.local_id;
+		initiator_id = rh.initiator_id;
+		acceptor_id = rh.acceptor_id;
+		return *this;
+	}
+
+	/// returns true, if the local link id is known and registered
+	bool isValid() const {
+		return isValid(*this);
+	}
+
+	bool isUnspecified() const {
+		return local_id == 0 && initiator_id == 0 && acceptor_id == 0;
+	}
+
+	/// returns true, if this is a local id only
+	bool isLocal() const {
+		return acceptor_id == 0 && initiator_id == 0;
+	}
+
+	/// returns true, if this is a remote id only
+	bool isRemote() const {
+		return local_id == 0;
+	}
+
+	/// returns true, if this is a full link id (with acceptor/initiator id)
+	bool isLink() const {
+		return acceptor_id != 0 && initiator_id != 0;
+	}
+
+	/// returns the local id
+	uint16_t getLocalId() const {
+		return local_id;
+	}
+
+	/// returns the remote id
+	uint16_t getRemoteId() const {
+		return local_id == initiator_id ? acceptor_id : initiator_id;
+	}
+
+	/// returns the initiators local link id
+	uint16_t getInitiatorId() const {
+		return initiator_id;
+	}
+
+	/// returns the acceptors local link id
+	uint16_t getAcceptorId() const {
+		return acceptor_id;
+	}
+
+	/// sets the local initiator id of the link
+	/// if id is unspecified a new local id is used as initiator id
+	void setInitiatorId( const LinkID& id = UNSPECIFIED ) {
+		assert(initiator_id == 0);
+		if ( id == UNSPECIFIED ) {
+			assert(local_id == 0);
+			local_id = LinkID::create().local_id;
+			initiator_id = local_id;
+		} else {
+			assert(local_id == acceptor_id && id.local_id == 0 && id.initiator_id != 0);
+			initiator_id = id.initiator_id;
+		}
+	}
+
+	/// sets the local acceptor id of the link
+	/// if id is unspecified a new local id is used as acceptor id
+	void setAcceptorId( const LinkID& id = UNSPECIFIED ) {
+		assert(acceptor_id == 0);
+		if ( id == UNSPECIFIED ) {
+			assert(local_id == 0);
+			local_id = LinkID::create().local_id;
+			acceptor_id = local_id;
+		} else {
+			assert(local_id == initiator_id && id.local_id == 0 && id.acceptor_id != 0);
+			acceptor_id = id.acceptor_id;
+		}
+	}
+
+	void combine( const LinkID& id ) {
+
+	}
+
+	/// returns a string representation of the link id
+	std::string toString() const {
+		char str[20];
+		if (isLocal())
+			sprintf(str, "l%04x", local_id);
+		else
+			sprintf(str, "i%04x.a%04x", initiator_id, acceptor_id );
+		return std::string(str);
+	}
+
+	/// returns the info of the link id
+	const char* getInfo() const {
+		return getInfo(*this);
+	}
+
+	/// convenience operators
+	bool operator==( const LinkID& rhs ) const { return compareTo(rhs) == 0; }
+	bool operator!=( const LinkID& rhs ) const { return compareTo(rhs) != 0; }
+	bool operator< ( const LinkID& rhs ) const { return compareTo(rhs) <  0; }
+	bool operator<=( const LinkID& rhs ) const { return compareTo(rhs) <= 0; }
+	bool operator> ( const LinkID& rhs ) const { return compareTo(rhs) >  0; }
+	bool operator>=( const LinkID& rhs ) const { return compareTo(rhs) >= 0; }
 };
 
+std::ostream& operator<<(std::ostream& s, const LinkID& id );
+
 typedef vector<LinkID> LinkIDs;
 
 }} // namespace ariba, utility
 
+sznBeginDefault( ariba::utility::LinkID, X ) {
+	if (X.isDeserializer()) local_id = 0;
+	X && initiator_id && acceptor_id;
+} sznEnd();
+
+
 #endif /* LINKID_H_ */
