]> git.meshlink.io Git - meshlink/commitdiff
Modified meshlink_invite to generate invites for submesh
authorLakshminarayana Gurram <lakshminarayana@elear.solutions>
Wed, 6 Feb 2019 02:47:30 +0000 (08:17 +0530)
committerGuus Sliepen <guus@meshlink.io>
Wed, 6 Feb 2019 09:28:05 +0000 (10:28 +0100)
examples/channels.c
examples/chat.c
examples/chatpp.cc
examples/manynodes.c
src/meshlink++.h
src/meshlink.c
src/meshlink.h
src/net_setup.c
src/node.h
src/submesh.c
src/submesh.h

index 2059b387e803dcd140cfa083b57953b9ba585f1f..d4e378f698a01d2912069d2585904139318b05eb 100644 (file)
@@ -96,7 +96,7 @@ static void parse_command(meshlink_handle_t *mesh, char *buf) {
                        return;
                }
 
-               invitation = meshlink_invite(mesh, arg);
+               invitation = meshlink_invite(mesh, NULL, arg);
 
                if(!invitation) {
                        fprintf(stderr, "Could not invite '%s': %s\n", arg, meshlink_strerror(meshlink_errno));
index c26a642de5fef96b59cadec75752814b2429f4a5..d0e511cab56fa578e384e468bb8d94032da7c355 100644 (file)
@@ -59,7 +59,7 @@ static void parse_command(meshlink_handle_t *mesh, char *buf) {
                        return;
                }
 
-               invitation = meshlink_invite(mesh, arg);
+               invitation = meshlink_invite(mesh, NULL, arg);
 
                if(!invitation) {
                        fprintf(stderr, "Could not invite '%s': %s\n", arg, meshlink_strerror(meshlink_errno));
index 10870ef55a85b635a725dfbecf2cca31fcf49f94..d3690404fc2869b3b8998c849eb5484b193b5382 100644 (file)
@@ -49,7 +49,7 @@ static void parse_command(meshlink::mesh *mesh, char *buf) {
                        return;
                }
 
-               invitation = mesh->invite(arg);
+               invitation = mesh->invite(NULL, arg);
 
                if(!invitation) {
                        fprintf(stderr, "Could not invite '%s': %s\n", arg, meshlink::strerror());
index 9e4a95c095c6b1b621f305c4dceb5cd20c1209fb..f9150ef73b19d390f261945d021b3611810e5c65 100644 (file)
@@ -208,7 +208,7 @@ static void parse_command(char *buf) {
                        return;
                }
 
-               invitation = meshlink_invite(mesh[nodeindex], arg);
+               invitation = meshlink_invite(mesh[nodeindex], NULL, arg);
 
                if(!invitation) {
                        fprintf(stderr, "Could not invite '%s': %s\n", arg, meshlink_strerror(meshlink_errno));
index f7b0e1ace4919e5b15530085cf96daed79194ade..b9889aa1898bed14f28a6f2d58ca48df31b50d3b 100644 (file)
@@ -537,8 +537,8 @@ public:
         *  @return             This function returns a string that contains the invitation URL.
         *                      The application should call free() after it has finished using the URL.
         */
-       char *invite(const char *name, uint32_t flags = 0) {
-               return meshlink_invite_ex(handle, name, flags);
+       char *invite(submesh *submesh, const char *name, uint32_t flags = 0) {
+               return meshlink_invite_ex(handle, submesh, name, flags);
        }
 
        /// Use an invitation to join a mesh.
index 0ea38dbb55c952c5ea69e0ab70181f4cb8f17706..d094452733712c2e1b02b3bbfaa09efce7e96cca 100644 (file)
@@ -60,6 +60,7 @@ const var_t variables[] = {
        {"ConnectTo", VAR_SERVER | VAR_MULTIPLE | VAR_SAFE},
        {"Name", VAR_SERVER},
        /* Host configuration */
+       {"SubMesh", VAR_HOST | VAR_SAFE},
        {"CanonicalAddress", VAR_HOST},
        {"Address", VAR_HOST | VAR_MULTIPLE},
        {"ECDSAPublicKey", VAR_HOST},
@@ -1305,6 +1306,7 @@ meshlink_handle_t *meshlink_open_ex(const meshlink_open_params_t *params) {
        mesh->discovery = true;
        mesh->invitation_timeout = 604800; // 1 week
        mesh->netns = params->netns;
+       mesh->submeshes = NULL;
 
        if(usingname) {
                mesh->name = xstrdup(params->name);
@@ -1418,6 +1420,7 @@ meshlink_handle_t *meshlink_open_ex(const meshlink_open_params_t *params) {
 
 meshlink_submesh_t *meshlink_submesh_open(meshlink_handle_t  *mesh, const char *submesh) {
        meshlink_submesh_t *s = NULL;
+
        if(!mesh) {
                logger(NULL, MESHLINK_ERROR, "No mesh handle given!\n");
                meshlink_errno = MESHLINK_EINVAL;
@@ -1432,7 +1435,7 @@ meshlink_submesh_t *meshlink_submesh_open(meshlink_handle_t  *mesh, const char *
 
        s = (meshlink_submesh_t *)lookup_submesh(mesh, submesh);
 
-       if (s) {
+       if(s) {
                logger(NULL, MESHLINK_ERROR, "SubMesh Already exists!\n");
                meshlink_errno = MESHLINK_EEXIST;
                return NULL;
@@ -2248,12 +2251,24 @@ void meshlink_set_invitation_timeout(meshlink_handle_t *mesh, int timeout) {
        mesh->invitation_timeout = timeout;
 }
 
-char *meshlink_invite_ex(meshlink_handle_t *mesh, const char *name, uint32_t flags) {
+char *meshlink_invite_ex(meshlink_handle_t *mesh, meshlink_submesh_t *submesh, const char *name, uint32_t flags) {
+       meshlink_submesh_t *s = NULL;
+
        if(!mesh) {
                meshlink_errno = MESHLINK_EINVAL;
                return NULL;
        }
 
+       if(submesh) {
+               s = (meshlink_submesh_t *)lookup_submesh(mesh, submesh->name);
+
+               if(s != submesh) {
+                       logger(mesh, MESHLINK_DEBUG, "Invalid SubMesh Handle.\n");
+                       meshlink_errno = MESHLINK_EINVAL;
+                       return NULL;
+               }
+       }
+
        pthread_mutex_lock(&(mesh->mesh_mutex));
 
        // Check validity of the new node's name
@@ -2341,6 +2356,11 @@ char *meshlink_invite_ex(meshlink_handle_t *mesh, const char *name, uint32_t fla
 
        // Fill in the details.
        fprintf(f, "Name = %s\n", name);
+
+       if(s) {
+               fprintf(f, "SubMesh = %s\n", s->name);
+       }
+
        fprintf(f, "ConnectTo = %s\n", mesh->self->name);
 
        // Copy Broadcast and Mode
@@ -2386,8 +2406,8 @@ char *meshlink_invite_ex(meshlink_handle_t *mesh, const char *name, uint32_t fla
        return url;
 }
 
-char *meshlink_invite(meshlink_handle_t *mesh, const char *name) {
-       return meshlink_invite_ex(mesh, name, 0);
+char *meshlink_invite(meshlink_handle_t *mesh, meshlink_submesh_t *submesh, const char *name) {
+       return meshlink_invite_ex(mesh, submesh, name, 0);
 }
 
 bool meshlink_join(meshlink_handle_t *mesh, const char *invitation) {
index 6e03343bfc6997558f1b91ec4a2808b1bf8145fa..b7c2fca6880a9fc507c4e26f79c817a6d816b181 100644 (file)
@@ -219,7 +219,7 @@ extern meshlink_handle_t *meshlink_open_ex(const meshlink_open_params_t *params)
 extern meshlink_handle_t *meshlink_open(const char *confbase, const char *name, const char *appname, dev_class_t devclass);
 
 /// Create Sub-Mesh.
-/** This function causes MeshLink to open a new Sub-Mesh network 
+/** This function causes MeshLink to open a new Sub-Mesh network
  *  create a new thread, which will handle all network I/O.
  *
  *  It is allowed to call this function even if MeshLink is already started, in which case it will return true.
@@ -693,6 +693,7 @@ extern void meshlink_set_invitation_timeout(meshlink_handle_t *mesh, int timeout
  *  The URL can only be used once, after the user has joined the mesh the URL is no longer valid.
  *
  *  @param mesh         A handle which represents an instance of MeshLink.
+ *  @param submesh      A handle which represents an instance of SubMesh.
  *  @param name         A nul-terminated C string containing the name that the invitee will be allowed to use in the mesh.
  *                      After this function returns, the application is free to overwrite or free @a name @a.
  *  @param flags        A bitwise-or'd combination of flags that controls how the URL is generated.
@@ -700,7 +701,7 @@ extern void meshlink_set_invitation_timeout(meshlink_handle_t *mesh, int timeout
  *  @return             This function returns a nul-terminated C string that contains the invitation URL, or NULL in case of an error.
  *                      The application should call free() after it has finished using the URL.
  */
-extern char *meshlink_invite_ex(meshlink_handle_t *mesh, const char *name, uint32_t flags);
+extern char *meshlink_invite_ex(meshlink_handle_t *mesh, meshlink_submesh_t *submesh, const char *name, uint32_t flags);
 
 /// Invite another node into the mesh.
 /** This function generates an invitation that can be used by another node to join the same mesh as the local node.
@@ -711,13 +712,14 @@ extern char *meshlink_invite_ex(meshlink_handle_t *mesh, const char *name, uint3
  *  Calling this function is equal to callen meshlink_invite_ex() with flags set to 0.
  *
  *  @param mesh         A handle which represents an instance of MeshLink.
+ *  @param submesh      A handle which represents an instance of SubMesh.
  *  @param name         A nul-terminated C string containing the name that the invitee will be allowed to use in the mesh.
  *                      After this function returns, the application is free to overwrite or free @a name @a.
  *
  *  @return             This function returns a nul-terminated C string that contains the invitation URL, or NULL in case of an error.
  *                      The application should call free() after it has finished using the URL.
  */
-extern char *meshlink_invite(meshlink_handle_t *mesh, const char *name);
+extern char *meshlink_invite(meshlink_handle_t *mesh, meshlink_submesh_t *submesh, const char *name);
 
 /// Use an invitation to join a mesh.
 /** This function allows the local node to join an existing mesh using an invitation URL generated by another node.
index 10fb37b0005c5df5ae73b35bf33a66a9591796ac..47ed32e0ec9e202b22cb1bf1e73433587b5f5eaf 100644 (file)
@@ -31,6 +31,7 @@
 #include "route.h"
 #include "utils.h"
 #include "xalloc.h"
+#include "submesh.h"
 
 bool node_read_ecdsa_public_key(meshlink_handle_t *mesh, node_t *n) {
        if(ecdsa_active(n->ecdsa)) {
@@ -156,6 +157,39 @@ exit:
        return n->devclass != 0;
 }
 
+bool node_read_submesh(meshlink_handle_t *mesh, node_t *n) {
+
+       splay_tree_t *config_tree;
+       char *p;
+
+       init_configuration(&config_tree);
+
+       if(!read_host_config(mesh, config_tree, n->name)) {
+               goto exit;
+       }
+
+       if(get_config_string(lookup_config(config_tree, "SubMesh"), &p)) {
+               n->submesh = NULL;
+
+               for list_each(submesh_t, s, mesh->submeshes) {
+                       if(!strcmp(p, s->name)) {
+                               n->submesh = s;
+                               break;
+                       }
+               }
+
+               if(!n->submesh) {
+                       n->submesh = (submesh_t *)meshlink_submesh_open(mesh, p);
+               }
+
+               free(p);
+       }
+
+exit:
+       exit_configuration(&config_tree);
+       return n->submesh != NULL;
+}
+
 bool node_write_devclass(meshlink_handle_t *mesh, node_t *n) {
 
        if((int)n->devclass < 0 || n->devclass > _DEV_CLASS_MAX) {
@@ -191,6 +225,41 @@ fail:
        return result;
 }
 
+bool node_write_submesh(meshlink_handle_t *mesh, node_t *n) {
+
+       if(!n->submesh) {
+               return false;
+       }
+
+       bool result = false;
+
+       splay_tree_t *config_tree;
+       init_configuration(&config_tree);
+
+       // ignore read errors; in case the file does not exist we will create it
+       read_host_config(mesh, config_tree, n->name);
+
+       config_t *cnf = lookup_config(config_tree, "SubMesh");
+
+       if(!cnf) {
+               cnf = new_config();
+               cnf->variable = xstrdup("SubMesh");
+               config_add(config_tree, cnf);
+       }
+
+       set_config_string(cnf, n->submesh->name);
+
+       if(!write_host_config(mesh, config_tree, n->name)) {
+               goto fail;
+       }
+
+       result = true;
+
+fail:
+       exit_configuration(&config_tree);
+       return result;
+}
+
 void load_all_nodes(meshlink_handle_t *mesh) {
        DIR *dir;
        struct dirent *ent;
@@ -212,12 +281,17 @@ void load_all_nodes(meshlink_handle_t *mesh) {
                node_t *n = lookup_node(mesh, ent->d_name);
 
                if(n) {
+                       if(n == mesh->self && !n->submesh) {
+                               node_read_submesh(mesh, n);
+                       }
+
                        continue;
                }
 
                n = new_node();
                n->name = xstrdup(ent->d_name);
                node_read_devclass(mesh, n);
+               node_read_submesh(mesh, n);
                node_add(mesh, n);
        }
 
@@ -463,6 +537,7 @@ bool setup_myself(meshlink_handle_t *mesh) {
 */
 bool setup_network(meshlink_handle_t *mesh) {
        init_connections(mesh);
+       init_submeshes(mesh);
        init_nodes(mesh);
        init_edges(mesh);
        init_requests(mesh);
index acbf2e8bfec4b866458fdc4e94d5959952065bc1..9fad554550f0da2b3cc62da77dc0ce6c21637403 100644 (file)
@@ -50,7 +50,7 @@ typedef struct node_t {
        dev_class_t devclass;
 
        struct meshlink_handle *mesh;           /* The mesh this node belongs to */
-       struct submesh_t *submesh;              /* Nodes Sub-Mesh Handle*/
+       struct submesh_t *submesh;              /* Nodes Sub-Mesh Handle*/
 
        int sock;                               /* Socket to use for outgoing UDP packets */
        sockaddr_t address;                     /* his real (internet) ip to send UDP packets to */
index 0a2bfb09357ed215f7119e52ef3ccacf0d26a946..317328c8a5e177df04ea026dff4971b75219a318 100644 (file)
@@ -67,12 +67,12 @@ void submesh_del(meshlink_handle_t *mesh, submesh_t *s) {
 submesh_t *lookup_submesh(struct meshlink_handle *mesh, const char *submesh_name) {
        submesh_t *submesh = NULL;
 
-       if ( !mesh->submeshes ) {
+       if(!mesh->submeshes) {
                return NULL;
        }
 
        for list_each(submesh_t, s, mesh->submeshes) {
-               if ( !strcmp(submesh_name, s->name) ) {
+               if(!strcmp(submesh_name, s->name)) {
                        submesh = s;
                        break;
                }
index 958ce9c7baeed8ffb5246880768923662524935b..b5d90b301d6ae726724c25b14fbc09ac79cab35e 100644 (file)
@@ -26,7 +26,7 @@ typedef struct submesh_t {
        char *name;                             /* name of this Sub-Mesh */
        void *priv;
 
-       struct meshlink_handle *mesh;                   /* the mesh this submesh belongs to */
+       struct meshlink_handle *mesh;                   /* the mesh this submesh belongs to */
 } submesh_t;
 
 extern void init_submeshes(struct meshlink_handle *mesh);