-peer review
[oweals/gnunet.git] / src / include / gnunet_testbed_service.h
index d36f5aa8e6f6ced4520b8d1158e7e3f3a3cac6b8..5563bd6be3088e6578ac6af6732bf3b22583466b 100644 (file)
@@ -29,6 +29,7 @@
 #define GNUNET_TESTBED_SERVICE_H
 
 #include "gnunet_util_lib.h"
+#include "gnunet_testing_lib-new.h"
 
 #ifdef __cplusplus
 extern "C"
@@ -117,7 +118,7 @@ GNUNET_TESTBED_host_create_with_id (uint32_t id,
  */
 unsigned int
 GNUNET_TESTBED_hosts_load_from_file (const char *filename,
-                                    struct GNUNET_TESTBED_Host **hosts);
+                                    struct GNUNET_TESTBED_Host ***hosts);
 
 
 /**
@@ -183,13 +184,6 @@ enum GNUNET_TESTBED_PeerInformationType
    */
   GNUNET_TESTBED_PIT_GENERIC = 0,
 
-  /**
-   * What host is the peer running on?  Returns a 'const struct
-   * GNUNET_TESTBED_Host *'.  Valid until
-   * 'GNUNET_TESTBED_operation_done' is called.
-   */
-  GNUNET_TESTBED_PIT_HOST,
-
   /**
    * What configuration is the peer using?  Returns a 'const struct
    * GNUNET_CONFIGURATION_Handle *'.  Valid until
@@ -315,41 +309,11 @@ struct GNUNET_TESTBED_EventInformation
       const char *emsg;
 
       /**
-       * Peer information type; captures which of the types
-       * in the 'op_result' is actually in use.
-       */
-      enum GNUNET_TESTBED_PeerInformationType pit;
-
-      /**
-       * Pointer to an operation-specific return value; NULL on error;
-       * can be NULL for certain operations.  Valid until
-       * 'GNUNET_TESTBED_operation_done' is called.
+       * No result (NULL pointer) or generic result
+       * (whatever the GNUNET_TESTBED_ConnectAdapter returned).
        */
-      union
-      {
-       /**
-        * No result (NULL pointer) or generic result
-        * (whatever the GNUNET_TESTBED_ConnectAdapter returned).
-        */
-       void *generic;
-
-       /**
-        * Identity of host running the peer.
-        */
-       struct GNUNET_TESTBED_Host *host;
-
-       /**
-        * Identity of the peer.
-        */
-       const struct GNUNET_PeerIdentity *pid;
-
-       /**
-        * Configuration of the peer.
-        */
-       const struct GNUNET_CONFIGURATION_Handle *cfg;
-
-      } op_result;
-
+      void *generic;
+      
     } operation_finished;   
 
 
@@ -402,13 +366,45 @@ struct GNUNET_TESTBED_ControllerProc;
 
 
 /**
- * Starts a controller process at the host
+ * Callback to signal successfull startup of the controller process
  *
- * @param host the host where the controller has to be started; NULL for localhost
- * @return the controller process handle
+ * @param cls the closure from GNUNET_TESTBED_controller_start()
+ * @param cfg the configuration with which the controller has been started;
+ *          NULL if status is not GNUNET_OK
+ * @param status GNUNET_OK if the startup is successfull; GNUNET_SYSERR if not,
+ *          GNUNET_TESTBED_controller_stop() shouldn't be called in this case
+ */
+typedef void (*GNUNET_TESTBED_ControllerStatusCallback) (void *cls, 
+                                                        const struct GNUNET_CONFIGURATION_Handle *cfg,
+                                                        int status);
+
+
+/**
+ * Starts a controller process at the host. 
+ *
+ * @param controller_ip the ip address of the controller. Will be set as TRUSTED
+ *          host when starting testbed controller at host
+ * @param host the host where the controller has to be started; NULL for
+ *          localhost
+ * @param cfg template configuration to use for the remote controller; the
+ *          remote controller will be started with a slightly modified
+ *          configuration (port numbers, unix domain sockets and service home
+ *          values are changed as per TESTING library on the remote host)
+ * @param cb function called when the controller is successfully started or
+ *          dies unexpectedly; GNUNET_TESTBED_controller_stop shouldn't be
+ *          called if cb is called with GNUNET_SYSERR as status. Will never be
+ *          called in the same task as 'GNUNET_TESTBED_controller_start'
+ *          (synchronous errors will be signalled by returning NULL). This
+ *          parameter cannot be NULL.
+ * @param cls closure for above callbacks
+ * @return the controller process handle, NULL on errors
  */
 struct GNUNET_TESTBED_ControllerProc *
-GNUNET_TESTBED_controller_start (struct GNUNET_TESTBED_Host *host);
+GNUNET_TESTBED_controller_start (const char *controller_ip,
+                                struct GNUNET_TESTBED_Host *host,
+                                const struct GNUNET_CONFIGURATION_Handle *cfg,
+                                 GNUNET_TESTBED_ControllerStatusCallback cb,
+                                void *cls);
 
 
 /**
@@ -528,28 +524,43 @@ GNUNET_TESTBED_cancel_registration (struct GNUNET_TESTBED_HostRegistrationHandle
 
 
 /**
- * Create a link from a 'master' controller to a slave controller.
- * Whenever the master controller is asked to start a peer at the
- * given 'delegated_host', it will delegate the request to the
- * specified slave controller.  Note that the slave controller runs at
- * the 'slave_host', which may or may not be the same host as the
- * 'delegated_host' (for hierarchical delegations).  The configuration
- * of the slave controller is given and to be used to either create
- * the slave controller or to connect to an existing slave controller
- * process.  'is_subordinate' specifies if the given slave controller
- * should be started and managed by the master controller, or if the
- * slave already has a master and this is just a secondary master that
- * is also allowed to use the existing slave.
+ * Callback to be called when an operation is completed
+ *
+ * @param cls the callback closure from functions generating an operation
+ * @param op the operation that has been finished
+ * @param emsg error message in case the operation has failed; will be NULL if
+ *          operation has executed successfully.
+ */
+typedef void (*GNUNET_TESTBED_OperationCompletionCallback) (void *cls,
+                                                            struct
+                                                            GNUNET_TESTBED_Operation
+                                                            *op,
+                                                            const char *emsg);
+
+
+/**
+ * Create a link from slave controller to delegated controller. Whenever the
+ * master controller is asked to start a peer at the delegated controller the
+ * request will be routed towards slave controller (if a route exists). The
+ * slave controller will then route it to the delegated controller. The
+ * configuration of the slave controller is given and to be used to either
+ * create the slave controller or to connect to an existing slave controller
+ * process.  'is_subordinate' specifies if the given slave controller should be
+ * started and managed by the master controller, or if the slave already has a
+ * master and this is just a secondary master that is also allowed to use the
+ * existing slave.
  *
  * @param master handle to the master controller who creates the association
- * @param delegated_host requests to which host should be delegated
- * @param slave_host which host is used to run the slave controller 
+ * @param delegated_host requests to which host should be delegated; cannot be NULL
+ * @param slave_host which host is used to run the slave controller; use NULL to
+ *          make the master controller connect to the delegated host
  * @param slave_cfg configuration to use for the slave controller
- * @param is_subordinate GNUNET_YES if the slave should be started (and stopped)
- *                       by the master controller; GNUNET_NO if we are just
- *                       allowed to use the slave via TCP/IP
+ * @param is_subordinate GNUNET_YES if the controller at delegated_host should
+ *          be started by the master controller; GNUNET_NO if we are just
+ *          allowed to use the slave via TCP/IP
+ * @return the operation handle
  */
-void
+struct GNUNET_TESTBED_Operation *
 GNUNET_TESTBED_controller_link (struct GNUNET_TESTBED_Controller *master,
                                struct GNUNET_TESTBED_Host *delegated_host,
                                struct GNUNET_TESTBED_Host *slave_host,
@@ -557,6 +568,46 @@ GNUNET_TESTBED_controller_link (struct GNUNET_TESTBED_Controller *master,
                                int is_subordinate);
 
 
+/**
+ * Same as the GNUNET_TESTBED_controller_link, however expects configuration in
+ * serialized and compressed
+ *
+ * @param master handle to the master controller who creates the association
+ * @param delegated_host requests to which host should be delegated; cannot be NULL
+ * @param slave_host which host is used to run the slave controller; use NULL to
+ *          make the master controller connect to the delegated host
+ * @param sxcfg serialized and compressed configuration
+ * @param sxcfg_size the size scfg
+ * @param scfg_size the size of uncompressed serialized configuration
+ * @param is_subordinate GNUNET_YES if the controller at delegated_host should
+ *          be started by the master controller; GNUNET_NO if we are just
+ *          allowed to use the slave via TCP/IP
+ * @return the operation handle
+ */
+struct GNUNET_TESTBED_Operation *
+GNUNET_TESTBED_controller_link_2 (struct GNUNET_TESTBED_Controller *master,
+                                 struct GNUNET_TESTBED_Host *delegated_host,
+                                 struct GNUNET_TESTBED_Host *slave_host,
+                                 const char *sxcfg,
+                                 size_t sxcfg_size,
+                                 size_t scfg_size,
+                                 int is_subordinate);
+
+
+/**
+ * Functions of this signature are called when a peer has been successfully
+ * created
+ *
+ * @param cls the closure from GNUNET_TESTBED_peer_create()
+ * @param peer the handle for the created peer; NULL on any error during
+ *          creation
+ * @param emsg NULL if peer is not NULL; else MAY contain the error description
+ */
+typedef void (*GNUNET_TESTBED_PeerCreateCallback) (void *cls,
+                                                  struct GNUNET_TESTBED_Peer *peer,
+                                                  const char *emsg);
+
+
 /**
  * Create the given peer at the specified host using the given
  * controller.  If the given controller is not running on the target
@@ -580,23 +631,43 @@ GNUNET_TESTBED_controller_link (struct GNUNET_TESTBED_Controller *master,
  *
  * @param controller controller process to use
  * @param host host to run the peer on
- * @param cfg configuration to use for the peer
- * @return handle to the peer (actual startup will happen asynchronously)
+ * @param cfg Template configuration to use for the peer. Should exist until
+ *          operation is cancelled or GNUNET_TESTBED_operation_done() is called
+ * @param cb the callback to call when the peer has been created
+ * @param cls the closure to the above callback
+ * @return the operation handle
  */
-struct GNUNET_TESTBED_Peer *
+struct GNUNET_TESTBED_Operation *
 GNUNET_TESTBED_peer_create (struct GNUNET_TESTBED_Controller *controller,
                            struct GNUNET_TESTBED_Host *host,
-                           const struct GNUNET_CONFIGURATION_Handle *cfg);
+                           const struct GNUNET_CONFIGURATION_Handle *cfg,
+                           GNUNET_TESTBED_PeerCreateCallback cb,
+                           void *cls);
+
+
+/**
+ * Functions of this signature are called when a peer has been successfully
+ * started or stopped.
+ *
+ * @param cls the closure from GNUNET_TESTBED_peer_start/stop()
+ * @param emsg NULL on success; otherwise an error description
+ */
+typedef void (*GNUNET_TESTBED_PeerChurnCallback) (void *cls,
+                                                 const char *emsg);
 
 
 /**
  * Start the given peer.
  *
  * @param peer peer to start
+ * @param pcc function to call upon completion
+ * @param pcc_cls closure for 'pcc'
  * @return handle to the operation
  */
 struct GNUNET_TESTBED_Operation *
-GNUNET_TESTBED_peer_start (struct GNUNET_TESTBED_Peer *peer);
+GNUNET_TESTBED_peer_start (struct GNUNET_TESTBED_Peer *peer,
+                          GNUNET_TESTBED_PeerChurnCallback pcc,
+                          void *pcc_cls);
 
 
 /**
@@ -605,22 +676,82 @@ GNUNET_TESTBED_peer_start (struct GNUNET_TESTBED_Peer *peer);
  * state of the peer).
  *
  * @param peer peer to stop
+ * @param pcc function to call upon completion
+ * @param pcc_cls closure for 'pcc'
  * @return handle to the operation
  */
 struct GNUNET_TESTBED_Operation *
-GNUNET_TESTBED_peer_stop (struct GNUNET_TESTBED_Peer *peer);
+GNUNET_TESTBED_peer_stop (struct GNUNET_TESTBED_Peer *peer,
+                         GNUNET_TESTBED_PeerChurnCallback pcc,
+                         void *pcc_cls);
 
 
 /**
- * Request information about a peer.
+ * Data returned from GNUNET_TESTBED_peer_get_information
+ */
+struct GNUNET_TESTBED_PeerInformation
+{
+  /**
+   * Peer information type; captures which of the types
+   * in the 'op_result' is actually in use.
+   */
+  enum GNUNET_TESTBED_PeerInformationType pit;
+  
+  /**
+   * The result of the get information operation; Choose according to the pit
+   */
+  union
+  { 
+    /**
+     * The configuration of the peer
+     */
+    struct GNUNET_CONFIGURATION_Handle *cfg;
+  
+    /**
+     * The identity of the peer
+     */
+    struct GNUNET_PeerIdentity *id;
+  } result;
+};
+
+
+/**
+ * Callback to be called when the requested peer information is available
+ *
+ * @param cb_cls the closure from GNUNET_TETSBED_peer_get_information()
+ * @param op the operation this callback corresponds to
+ * @param pinfo the result; will be NULL if the operation has failed
+ * @param emsg error message if the operation has failed; will be NULL if the
+ *          operation is successfull
+ */
+typedef void (*GNUNET_TESTBED_PeerInfoCallback) (void *cb_cls,
+                                                struct GNUNET_TESTBED_Operation
+                                                *op,
+                                                const struct
+                                                GNUNET_TESTBED_PeerInformation
+                                                *pinfo,
+                                                const char *emsg);
+
+
+/**
+ * Request information about a peer. The controller callback will not be called
+ * with event type GNUNET_TESTBED_ET_OPERATION_FINISHED when result for this
+ * operation is available. Instead, the GNUNET_TESTBED_PeerInfoCallback() will
+ * be called.
  *
  * @param peer peer to request information about
  * @param pit desired information
+ * @param cb the convenience callback to be called when results for this
+ *          operation are available
+ * @param cb_cls the closure for the above callback
  * @return handle to the operation
  */
 struct GNUNET_TESTBED_Operation *
 GNUNET_TESTBED_peer_get_information (struct GNUNET_TESTBED_Peer *peer,
-                                    enum GNUNET_TESTBED_PeerInformationType pit);
+                                    enum GNUNET_TESTBED_PeerInformationType
+                                    pit,
+                                    GNUNET_TESTBED_PeerInfoCallback cb,
+                                    void *cb_cls);
 
 
 /**
@@ -829,6 +960,8 @@ GNUNET_TESTBED_underlay_configure_topology (void *op_cls,
  * and asks 'p2' to connect to 'p1'.
  *
  * @param op_cls closure argument to give with the operation event
+ * @param cb the callback to call when this operation has finished
+ * @param cb_cls the closure for the above callback
  * @param p1 first peer
  * @param p2 second peer
  * @return handle to the operation, NULL if connecting these two
@@ -837,6 +970,8 @@ GNUNET_TESTBED_underlay_configure_topology (void *op_cls,
  */
 struct GNUNET_TESTBED_Operation *
 GNUNET_TESTBED_overlay_connect (void *op_cls,
+                                GNUNET_TESTBED_OperationCompletionCallback cb,
+                                void *cb_cls,
                                struct GNUNET_TESTBED_Peer *p1,
                                struct GNUNET_TESTBED_Peer *p2);
 
@@ -889,6 +1024,7 @@ GNUNET_TESTBED_overlay_configure_topology (void *op_cls,
  * Ask the testbed controller to write the current overlay topology to
  * a file.  Naturally, the file will only contain a snapshot as the
  * topology may evolve all the time.
+ * FIXME: needs continuation!?
  *
  * @param controller overlay controller to inspect
  * @param filename name of the file the topology should
@@ -904,7 +1040,9 @@ GNUNET_TESTBED_overlay_write_topology_to_file (struct GNUNET_TESTBED_Controller
  * a service.
  * 
  * @param cls closure
- * @param cfg configuration of the peer to connect to
+ * @param cfg configuration of the peer to connect to; will be available until
+ *          GNUNET_TESTBED_operation_done() is called on the operation returned
+ *          from GNUNET_TESTBED_service_connect()
  * @return service handle to return in 'op_result', NULL on error
  */
 typedef void * (*GNUNET_TESTBED_ConnectAdapter)(void *cls,
@@ -922,6 +1060,25 @@ typedef void (*GNUNET_TESTBED_DisconnectAdapter)(void *cls,
                                                 void *op_result);
 
 
+/**
+ * Callback to be called when a service connect operation is completed
+ *
+ * @param cls the callback closure from functions generating an operation
+ * @param op the operation that has been finished
+ * @param ca_result the service handle returned from GNUNET_TESTBED_ConnectAdapter()
+ * @param emsg error message in case the operation has failed; will be NULL if
+ *          operation has executed successfully.
+ */
+typedef void (*GNUNET_TESTBED_ServiceConnectCompletionCallback) (void *cls,
+                                                                struct
+                                                                GNUNET_TESTBED_Operation
+                                                                *op,
+                                                                void
+                                                                *ca_result, 
+                                                                const char
+                                                                *emsg );
+
+
 /**
  * Connect to a service offered by the given peer.  Will ensure that
  * the request is queued to not overwhelm our ability to create and
@@ -936,6 +1093,8 @@ typedef void (*GNUNET_TESTBED_DisconnectAdapter)(void *cls,
  * @param op_cls closure to pass in operation event
  * @param peer peer that runs the service
  * @param service_name name of the service to connect to
+ * @param cb the callback to call when this operation finishes
+ * @param cb_cls closure for the above callback
  * @param ca helper function to establish the connection
  * @param da helper function to close the connection
  * @param cada_cls closure for ca and da
@@ -945,6 +1104,8 @@ struct GNUNET_TESTBED_Operation *
 GNUNET_TESTBED_service_connect (void *op_cls,
                                struct GNUNET_TESTBED_Peer *peer,
                                const char *service_name,
+                                GNUNET_TESTBED_ServiceConnectCompletionCallback cb,
+                                void *cb_cls,
                                GNUNET_TESTBED_ConnectAdapter ca,
                                GNUNET_TESTBED_DisconnectAdapter da,
                                void *cada_cls);
@@ -1039,6 +1200,44 @@ void
 GNUNET_TESTBED_destroy (struct GNUNET_TESTBED_Testbed *testbed);
 
 
+/**
+ * Callback function to process statistic values from all peers.
+ *
+ * @param cls closure
+ * @param peer the peer the statistic belong to
+ * @param subsystem name of subsystem that created the statistic
+ * @param name the name of the datum
+ * @param value the current value
+ * @param is_persistent GNUNET_YES if the value is persistent, GNUNET_NO if not
+ * @return GNUNET_OK to continue, GNUNET_SYSERR to abort iteration
+ */
+typedef int (*GNUNET_TESTBED_StatisticsIterator) (void *cls,
+                                                 const struct GNUNET_TESTBED_Peer *peer,
+                                                 const char *subsystem,
+                                                 const char *name,
+                                                 uint64_t value,
+                                                 int is_persistent);
+
+
+/**
+ * Convenience method that iterates over all (running) peers 
+ * and retrieves all statistics from each peer.
+ *
+ * @param num_peers number of peers to iterate over
+ * @param peers array of peers to iterate over
+ * @param proc processing function for each statistic retrieved
+ * @param cont continuation to call once call is completed(?)
+ * @param cls closure to pass to proc and cont
+ * @return operation handle to cancel the operation
+ */
+struct GNUNET_TESTBED_Operation *
+GNUNET_TESTBED_get_statistics (unsigned int num_peers,
+                              struct GNUNET_TESTBED_Peer **peers,
+                               GNUNET_TESTBED_StatisticsIterator proc,
+                               GNUNET_TESTBED_OperationCompletionCallback cont,
+                               void *cls);
+
+
 /**
  * Convenience method for running a testbed with
  * a single call.  Underlay and overlay topology
@@ -1053,12 +1252,16 @@ GNUNET_TESTBED_destroy (struct GNUNET_TESTBED_Testbed *testbed);
  * @param host_filename name of the file with the 'hosts', NULL
  *        to run everything on 'localhost'
  * @param cfg configuration to use (for testbed, controller and peers)
- * @param num_peers number of peers to start; FIXME: maybe put that ALSO into cfg?
+ * @param num_peers number of peers to start; FIXME: maybe put that ALSO into
+ *        cfg?; should be greater than 0
  * @param event_mask bit mask with set of events to call 'cc' for;
  *                   or-ed values of "1LL" shifted by the
  *                   respective 'enum GNUNET_TESTBED_EventType'
  *                   (i.e.  "(1LL << GNUNET_TESTBED_ET_CONNECT) || ...")
- * @param cc controller callback to invoke on events
+ * @param cc controller callback to invoke on events; This callback is called
+ *        for all peer start events even if GNUNET_TESTBED_ET_PEER_START isn't
+ *        set in the event_mask as this is the only way get access to the
+ *        handle of each peer
  * @param cc_cls closure for cc
  * @param master task to run once the testbed is ready
  * @param master_cls closure for 'task'.
@@ -1105,7 +1308,16 @@ typedef void (*GNUNET_TESTBED_TestMaster)(void *cls,
  * @param testname name of the testcase (to configure logging, etc.)
  * @param cfg_filename configuration filename to use
  *              (for testbed, controller and peers)
- * @param num_peers number of peers to start
+ * @param num_peers number of peers to start; should be greter than 0
+ * @param event_mask bit mask with set of events to call 'cc' for;
+ *                   or-ed values of "1LL" shifted by the
+ *                   respective 'enum GNUNET_TESTBED_EventType'
+ *                   (i.e.  "(1LL << GNUNET_TESTBED_ET_CONNECT) || ...")
+ * @param cc controller callback to invoke on events; This callback is called
+ *        for all peer start events even if GNUNET_TESTBED_ET_PEER_START isn't
+ *        set in the event_mask as this is the only way get access to the
+ *        handle of each peer
+ * @param cc_cls closure for cc
  * @param test_master task to run once the test is ready
  * @param test_master_cls closure for 'task'.
  */
@@ -1113,6 +1325,9 @@ void
 GNUNET_TESTBED_test_run (const char *testname,
                         const char *cfg_filename,
                         unsigned int num_peers,
+                         uint64_t event_mask,
+                         GNUNET_TESTBED_ControllerCallback cc,
+                         void *cc_cls,
                         GNUNET_TESTBED_TestMaster test_master,
                         void *test_master_cls);