summaryrefslogtreecommitdiff
path: root/src/irmd
diff options
context:
space:
mode:
Diffstat (limited to 'src/irmd')
-rw-r--r--src/irmd/CMakeLists.txt1
-rw-r--r--src/irmd/api_table.c115
-rw-r--r--src/irmd/api_table.h46
-rw-r--r--src/irmd/main.c75
4 files changed, 233 insertions, 4 deletions
diff --git a/src/irmd/CMakeLists.txt b/src/irmd/CMakeLists.txt
index 89fbae08..ca068703 100644
--- a/src/irmd/CMakeLists.txt
+++ b/src/irmd/CMakeLists.txt
@@ -6,6 +6,7 @@ include_directories(${CMAKE_BINARY_DIR}/include)
set(SOURCE_FILES
# Add source files here
+ api_table.c
irm_flow.c
main.c
reg_api.c
diff --git a/src/irmd/api_table.c b/src/irmd/api_table.c
new file mode 100644
index 00000000..b62b2b55
--- /dev/null
+++ b/src/irmd/api_table.c
@@ -0,0 +1,115 @@
+/*
+ * Ouroboros - Copyright (C) 2016
+ *
+ * The IPC Resource Manager - Application Instance Table
+ *
+ * Dimitri Staessens <dimitri.staessens@intec.ugent.be>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#include <ouroboros/config.h>
+#include <ouroboros/list.h>
+#include <ouroboros/errno.h>
+
+#include "api_table.h"
+
+#include <stdlib.h>
+
+struct api_entry * api_entry_create(pid_t api,
+ char * apn,
+ char * ap_subset)
+{
+ struct api_entry * e = malloc(sizeof(*e));
+ if (e == NULL)
+ return NULL;
+
+ INIT_LIST_HEAD(&e->next);
+
+ e->api = api;
+ e->apn = apn;
+ e->ap_subset = ap_subset;
+
+ return e;
+}
+
+void api_entry_destroy(struct api_entry * e)
+{
+ if (e->apn != NULL)
+ free(e->apn);
+ if (e->ap_subset != NULL)
+ free(e->ap_subset);
+ free(e);
+}
+
+int api_table_add_api(struct list_head * api_table,
+ pid_t api, char * apn, char * ap_subset)
+{
+ if (apn == NULL)
+ return -EINVAL;
+
+ struct api_entry * e = api_entry_create(api, apn, ap_subset);
+ if (e == NULL)
+ return -ENOMEM;
+
+ list_add(&e->next, api_table);
+
+ return 0;
+}
+
+void api_table_del_api(struct list_head * api_table, pid_t api)
+{
+ struct list_head * p;
+ struct list_head * h;
+
+ list_for_each_safe(p, h, api_table) {
+ struct api_entry * e =
+ list_entry(p, struct api_entry, next);
+
+ if (api == e->api) {
+ list_del(&e->next);
+ api_entry_destroy(e);
+ }
+ }
+}
+
+char * api_table_get_apn(struct list_head * api_table, pid_t api)
+{
+ struct list_head * h;
+
+ list_for_each(h, api_table) {
+ struct api_entry * e =
+ list_entry(h, struct api_entry, next);
+
+ if (api == e->api)
+ return e->apn;
+ }
+
+ return NULL;
+}
+char * api_table_get_ap_subset(struct list_head * api_table, pid_t api)
+{
+ struct list_head * h;
+
+ list_for_each(h, api_table) {
+ struct api_entry * e =
+ list_entry(h, struct api_entry, next);
+
+ if (api == e->api)
+ return e->ap_subset;
+ }
+
+ return NULL;
+}
diff --git a/src/irmd/api_table.h b/src/irmd/api_table.h
new file mode 100644
index 00000000..694de6da
--- /dev/null
+++ b/src/irmd/api_table.h
@@ -0,0 +1,46 @@
+/*
+ * Ouroboros - Copyright (C) 2016
+ *
+ * The IPC Resource Manager - Application Instance Table
+ *
+ * Dimitri Staessens <dimitri.staessens@intec.ugent.be>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#ifndef OUROBOROS_IRMD_API_TABLE_H
+#define OUROBOROS_IRMD_API_TABLE_H
+
+#include <unistd.h>
+
+struct api_entry {
+ struct list_head next;
+ pid_t api;
+ char * apn;
+ char * ap_subset; /* unique instance identifier */
+};
+
+struct api_entry * api_entry_create(pid_t api, char * apn, char * ap_subset);
+void api_entry_destroy(struct api_entry * e);
+
+int api_table_add_api(struct list_head * api_table,
+ pid_t api,
+ char * apn,
+ char * ap_subset);
+void api_table_del_api(struct list_head * api_table, pid_t api);
+char * api_table_get_apn(struct list_head * api_table, pid_t api);
+char * api_table_get_ap_subset(struct list_head * api_table, pid_t api);
+
+#endif /* OUROBOROS_IRMD_API_TABLE_H */
diff --git a/src/irmd/main.c b/src/irmd/main.c
index e36fb98e..55764941 100644
--- a/src/irmd/main.c
+++ b/src/irmd/main.c
@@ -43,6 +43,7 @@
#include "utils.h"
#include "registry.h"
#include "irm_flow.h"
+#include "api_table.h"
#include <sys/socket.h>
#include <sys/un.h>
@@ -78,8 +79,6 @@ struct spawned_api {
pid_t api;
};
-/* keeps track of port_id's between N and N - 1 */
-
struct irm {
/* FIXME: list of ipcps could be merged into the registry */
struct list_head ipcps;
@@ -87,6 +86,7 @@ struct irm {
struct list_head registry;
pthread_rwlock_t reg_lock;
+ struct list_head api_table;
struct list_head spawned_apis;
/* keep track of all flows in this processing system */
@@ -717,14 +717,59 @@ static int ap_unreg(char * name,
return ret;
}
+static int api_bind(pid_t api, char * apn, char * ap_subset)
+{
+ int ret = 0;
+ char * apn_dup;
+ char * ap_s_dup = ap_subset;
+ if (apn == NULL)
+ return -EINVAL;
+
+ pthread_rwlock_rdlock(&irmd->state_lock);
+
+ if (irmd->state != IRMD_RUNNING) {
+ pthread_rwlock_unlock(&irmd->state_lock);
+ return -EPERM;
+ }
+
+ pthread_rwlock_wrlock(&irmd->reg_lock);
+
+ apn_dup = strdup(apn);
+ if (apn_dup == NULL) {
+ pthread_rwlock_unlock(&irmd->reg_lock);
+ pthread_rwlock_unlock(&irmd->state_lock);
+ return -ENOMEM;
+ }
+
+ if (ap_subset != NULL) {
+ ap_s_dup = strdup(ap_subset);
+ if (ap_s_dup == NULL) {
+ pthread_rwlock_unlock(&irmd->reg_lock);
+ pthread_rwlock_unlock(&irmd->state_lock);
+ return -ENOMEM;
+ }
+ }
+
+ ret = api_table_add_api(&irmd->api_table,
+ api,
+ apn_dup,
+ ap_s_dup);
+
+ pthread_rwlock_unlock(&irmd->reg_lock);
+ pthread_rwlock_unlock(&irmd->state_lock);
+
+ return ret;
+}
+
static struct irm_flow * flow_accept(pid_t api,
- char * srv_ap_name,
char ** dst_ae_name)
{
struct irm_flow * f = NULL;
struct reg_entry * rne = NULL;
struct reg_api * rgi = NULL;
+ char * srv_ap_name;
+
pthread_rwlock_rdlock(&irmd->state_lock);
if (irmd->state != IRMD_RUNNING) {
@@ -734,6 +779,10 @@ static struct irm_flow * flow_accept(pid_t api,
pthread_rwlock_wrlock(&irmd->reg_lock);
+ srv_ap_name = api_table_get_apn(&irmd->api_table, api);
+ if (srv_ap_name == NULL)
+ return NULL;
+
rne = registry_get_entry_by_apn(&irmd->registry, srv_ap_name);
if (rne == NULL) {
pthread_rwlock_unlock(&irmd->reg_lock);
@@ -1458,6 +1507,18 @@ void * irm_flow_cleaner()
}
}
+ list_for_each_safe(pos, n, &irmd->api_table) {
+ struct api_entry * e =
+ list_entry(pos, struct api_entry, next);
+
+ if (kill(e->api, 0) < 0) {
+ LOG_INFO("Instance %d removed from api table.",
+ e->api);
+ list_del(&e->next);
+ api_entry_destroy(e);
+ }
+ }
+
pthread_rwlock_unlock(&irmd->reg_lock);
pthread_rwlock_unlock(&irmd->state_lock);
@@ -1542,6 +1603,12 @@ void * mainloop()
msg->ap_name,
msg->opts);
break;
+ case IRM_MSG_CODE__IRM_API_BIND:
+ ret_msg.has_result = true;
+ ret_msg.result = api_bind(msg->api,
+ msg->ap_name,
+ msg->ap_subset);
+ break;
case IRM_MSG_CODE__IRM_LIST_IPCPS:
ret_msg.n_apis = list_ipcps(msg->dst_name,
&apis);
@@ -1562,7 +1629,6 @@ void * mainloop()
break;
case IRM_MSG_CODE__IRM_FLOW_ACCEPT:
e = flow_accept(msg->api,
- msg->ap_name,
&ret_msg.ae_name);
if (e == NULL) {
@@ -1700,6 +1766,7 @@ static struct irm * irm_create()
}
INIT_LIST_HEAD(&irmd->ipcps);
+ INIT_LIST_HEAD(&irmd->api_table);
INIT_LIST_HEAD(&irmd->spawned_apis);
INIT_LIST_HEAD(&irmd->registry);
INIT_LIST_HEAD(&irmd->irm_flows);