Index: freeDiameter/CMakeLists.txt
===================================================================
--- freeDiameter/CMakeLists.txt	(revision 1)
+++ freeDiameter/CMakeLists.txt	(revision 2)
@@ -18,4 +18,7 @@
 TARGET_LINK_LIBRARIES(freeDiameterd libfreeDiameter ${FD_LIBS})
 
+# Save the list of files, if needed
+SET(FD_COMMON_SRC ${FD_COMMON_SRC} PARENT_SCOPE)
+
 # The unary tests directory
 OPTION(SKIP_TESTS "Skip compilation of the tests?" OFF)
Index: freeDiameter/tests/CMakeLists.txt
===================================================================
--- freeDiameter/tests/CMakeLists.txt	(revision 1)
+++ freeDiameter/tests/CMakeLists.txt	(revision 2)
@@ -20,8 +20,9 @@
 # Some parameters for the tests
 
-# Add this flag to add some debug information in the tests themselves
 ADD_DEFINITIONS(-DTEST_DEBUG)
+ADD_DEFINITIONS(-DTRACE_LEVEL=NONE)
 
 INCLUDE_DIRECTORIES( ".." )
+INCLUDE_DIRECTORIES( "../../libfreeDiameter" )
 
 SET(TEST_COMMON_SRC "")
@@ -35,4 +36,8 @@
 # ENDFOREACH(SRC_FILE)
 
+FOREACH( SRC_FILE ${LFD_SRC})
+   SET(TEST_COMMON_SRC ${TEST_COMMON_SRC} "../../libfreeDiameter/${SRC_FILE}")
+ENDFOREACH(SRC_FILE)
+
 # Create an archive with the daemon common files (all but main)
 ADD_LIBRARY(fDcore STATIC ${TEST_COMMON_SRC})
@@ -43,5 +48,5 @@
 FOREACH( TEST ${TEST_LIST} )
    ADD_EXECUTABLE(${TEST} ${TEST}.c tests.h)
-   TARGET_LINK_LIBRARIES(${TEST} libfreeDiameter fDcore ${FD_LIBS})
+   TARGET_LINK_LIBRARIES(${TEST} fDcore ${FD_LIBS})
    ADD_TEST(${TEST} ${EXECUTABLE_OUTPUT_PATH}/${TEST})
 ENDFOREACH( TEST )
Index: freeDiameter/tests/testmesg.c
===================================================================
--- freeDiameter/tests/testmesg.c	(revision 1)
+++ freeDiameter/tests/testmesg.c	(revision 2)
@@ -436,5 +436,5 @@
 				memset(&buf, 0, sizeof(buf)); /* Test that the OS value is really copied */
 				CHECK( 0, fd_msg_update_length ( avpi ) );
-				#if 1
+				#if 0
 				fd_log_debug("AVP octet string, 'This\\0 is a b...'\n");
 				fd_msg_dump_one(0, avpi);
Index: freeDiameter/tests/tests.h
===================================================================
--- freeDiameter/tests/tests.h	(revision 1)
+++ freeDiameter/tests/tests.h	(revision 2)
@@ -52,6 +52,4 @@
 #endif /* TEST_TIMEOUT */
 
-static int test_verbosity = 0;
-
 /* Standard includes */
 #include <getopt.h>
@@ -76,7 +74,9 @@
 }
 
+static int test_verbo = 0;
+
 /* Define the standard check routines */
 #define CHECK( _val, _assert ){				\
-	if (test_verbosity > 0) {			\
+	if (test_verbo > 0) {				\
 		fprintf(stderr,				\
 			"%s:%-4d: CHECK( " #_assert " == "\
@@ -111,9 +111,9 @@
 		switch (c) {
 			case 'd':	/* Increase verbosity of debug messages.  */
-				test_verbosity++;
+				test_verbo++;
 				break;
 				
-			case 'q':	/* Decrease verbosity then remove debug messages.  */
-				test_verbosity--;
+			case 'q':	/* Decrease verbosity.  */
+				test_verbo--;
 				break;
 			
@@ -126,4 +126,5 @@
 		}
 	}
+	fd_g_debug_lvl = (test_verbo > 0) ? (test_verbo - 1) : 0;
 	if (!no_timeout)
 		alarm(TEST_TIMEOUT);
Index: include/freeDiameter/libfreeDiameter.h
===================================================================
--- include/freeDiameter/libfreeDiameter.h	(revision 1)
+++ include/freeDiameter/libfreeDiameter.h	(revision 2)
@@ -122,5 +122,4 @@
 char * fd_log_time ( char * buf, size_t len );
 
-/************************** DEBUG MACROS ************************************/
 
 /* levels definitions */
@@ -137,8 +136,11 @@
 #endif /* TRACE_LEVEL */
 
-/* The level of the file being compiled */
+/* The level of the file being compiled. */
 static int local_debug_level = TRACE_LEVEL;
 
-/* helper macros (pre-processor hacks) */
+/* A global level, changed by configuration or cmd line for example. default is 0. */
+extern int fd_g_debug_lvl;
+
+/* helper macros (pre-processor hacks to allow macro arguments) */
 #define __str( arg )  #arg
 #define _stringize( arg ) __str( arg )
@@ -146,5 +148,5 @@
 #define _aggregate( arg1, arg2 ) __agr( arg1, arg2 )
 
-/* Some portability tricks to get nice function name in __PRETTY_FUNCTION__ */
+/* Some portability code to get nice function name in __PRETTY_FUNCTION__ */
 #if __STDC_VERSION__ < 199901L
 # if __GNUC__ >= 2
@@ -159,7 +161,7 @@
 
 /* Boolean for tracing at a certain level */
-#define TRACE_BOOL(_level_) ( (_level_) <= local_debug_level )
-
-/* The general debug macro, each call results in two lines of debug messages */
+#define TRACE_BOOL(_level_) ( (_level_) <= local_debug_level + fd_g_debug_lvl )
+
+/* The general debug macro, each call results in two lines of debug messages (change the macro for more compact output) */
 #define TRACE_DEBUG(level,format,args... ) {											\
 	if ( TRACE_BOOL(level) ) {												\
@@ -173,13 +175,13 @@
 }
 
-/* Helper for function entry */
+/* Helper for function entry -- for very detailed trace of the execution */
 #define TRACE_ENTRY(_format,_args... ) \
 	TRACE_DEBUG(FCTS, "->%s (" #_args ") = (" _format ") >", __PRETTY_FUNCTION__, ##_args );
 
-/* Helper for debugging by adding traces */
+/* Helper for debugging by adding traces -- for debuging a specific location of the code */
 #define TRACE_HERE()	\
-	TRACE_DEBUG(INFO, " -- debug checkpoint -- ");
-
-/* Helper for tracing the CHECK_* macros bellow */
+	TRACE_DEBUG(NONE, " -- debug checkpoint -- ");
+
+/* Helper for tracing the CHECK_* macros bellow -- very very verbose code execution! */
 #define TRACE_DEBUG_ALL( str ) 	\
 	TRACE_DEBUG(CALL, str );
@@ -403,5 +405,5 @@
 }
 
-/* Cleanups for cancellation (all threads should be safely cancelable!) */
+/* Cleanups for cancellation (all threads should be safely cancelable...) */
 static __inline__ void fd_cleanup_mutex( void * mutex )
 {
@@ -1274,6 +1276,97 @@
 #define ER_DIAMETER_REDIRECT_INDICATION		3006
 
-/* Iterator on the rules of a parent object */
-int fd_dict_iterate_rules ( struct dict_object *parent, void * data, int (*cb)(void *, struct dict_rule_data *) );
+
+/*============================================================*/
+/*                         SESSIONS                           */
+/*============================================================*/
+
+
+
+/*
+ * The libfreeDiameter does not provide a full support of the sessions state machines as described in the RFC3588.
+ * It only provides a basic support allowing an extension to associate some state with a session identifier, and retrieve 
+ * this data later.
+ *
+ * A session is an opaque object, associated with a value of a Session-Id AVP.
+ * An extension that wants to associate data with the session must first register as session module client 
+ * with the sess_regext function to get an identifier object (sess_reg_t).
+ * 
+ * The module manages tuplets ( sess_id_t *, sess_reg_t *, void *). The following functions are used to manage these tuplets:
+ * sess_data_reg  : associate a pointer with a given session for a given module client.
+ * sess_data_dereg: removes an association.
+ * sess_data_get  : get the pointer associated with an association without changing it.
+ *
+ * Note that creating an association calls sess_link as a side effect, and removing the association calls sess_unlink.
+ *
+ * QUICK TUTORIAL:
+ *  For an extension that wants to implement a session state machine, here is a quick guide.
+ *
+ * First, the extension must define a structure to save the session state, for example appstate_t.
+ *
+ * Since the extension will use the session module, it creates a sess_reg_t by calling sess_regext.
+ *
+ * If the extension behaves as a client, it receives external events that trig the start of a new sessions.
+ * When such event occurs, the extension calls sess_new with the appropriate parameters to create a new session.
+ * It initializes an appstate_t structure with the data of this session and creates an association with sess_data_reg (%).
+ * Then it creates a message (application-specific) to request authentication and/or authorization for the service
+ * and the message is sent.
+ *
+ * Later, assuming that the extension has registered appropriate callbacks in the dispatcher module, when a message
+ * is received, the extension can retrieve the state of the session with the sess_data_get function.
+ *
+ * Finaly, when the extension decides to terminate the session (timer, or as result of a message exchange), it
+ * calls sess_data_dereg in order to destroy the binding in the daemon. When last message refering this session is freed,
+ * the session data is freed.
+ *
+ * (%) A this time, the extension must call sess_unlink in order to counter the effects of the sess_new function.
+ * This allows to have the session destroyed when no more data is associated to it.
+
+
+
+/*============================================================*/
+/*                         DISPATCH                           */
+/*============================================================*/
+
+/* The dispatch process consists in passing a message to some handlers
+ (typically provided by extensions) based on its content (app id, cmd code...) */
+
+/* The dispatch module has two main roles:
+ *  - help determine if a message can be handled locally (during the routing step)
+ *  - pass the message to the callback(s) that will handle it (during the dispatch step)
+ *
+ * These are the possibilities for registering a callback:
+ *
+ * -> For All messages.
+ *  This callback is called for all messages that are handled locally. This should be used only
+ *  internally by the daemon, or for debug purpose.
+ *
+ * -> by AVP value (constants).
+ *  This callback will be called when a message is received and contains a certain AVP with a specified value.
+ *
+ * -> by AVP.
+ *  This callback will be called when the received message contains a certain AVP.
+ *
+ * -> by command-code.
+ *  This callback will be called when the message is a specific command.
+ *
+ * -> by application.
+ *  This callback will be called when the message has a specific application-id.
+ *
+ * ( by vendor: would this be useful? it may be added later)
+ *
+ * Note that several criteria may be selected at the same time, for example command-code AND application id.
+ *
+ * When a callback is called, it receives the message as parameter, and eventually a pointer to 
+ * the AVP in the message when this is appropriate.
+ *
+ * The callback must process the message, and eventually create an answer to it. See the definition
+ * bellow for more information.
+ *
+ * If no callback has handled the message, a default handler will be called with the effect of
+ * requeuing the message for forwarding on the network to another peer (for requests, if possible), or 
+ * discarding the message (for answers).
+ */
+
+
 
 
Index: libfreeDiameter/CMakeLists.txt
===================================================================
--- libfreeDiameter/CMakeLists.txt	(revision 1)
+++ libfreeDiameter/CMakeLists.txt	(revision 2)
@@ -24,2 +24,5 @@
 TARGET_LINK_LIBRARIES(libfreeDiameter ${FD_LIBS})
 
+# Save the list of files for testcases in the daemon's directory
+SET(LFD_SRC ${LFD_SRC} PARENT_SCOPE)
+
Index: libfreeDiameter/libfD.h
===================================================================
--- libfreeDiameter/libfD.h	(revision 1)
+++ libfreeDiameter/libfD.h	(revision 2)
@@ -46,4 +46,8 @@
 void fd_msg_eteid_init(void);
 
+/* Iterator on the rules of a parent object */
+int fd_dict_iterate_rules ( struct dict_object *parent, void * data, int (*cb)(void *, struct dict_rule_data *) );
+
+
 
 #endif /* _LIBFD_H */
Index: libfreeDiameter/log.c
===================================================================
--- libfreeDiameter/log.c	(revision 1)
+++ libfreeDiameter/log.c	(revision 2)
@@ -40,4 +40,5 @@
 pthread_mutex_t fd_log_lock = PTHREAD_MUTEX_INITIALIZER;
 pthread_key_t	fd_log_thname;
+int fd_g_debug_lvl = 0;
 
 /* Log a debug message */
