Previously trying to create an event group with no name (=NULL) caused a
segfault. Fix this and test it in the validation suite.

Signed-off-by: Matias Elo <matias....@nokia.com>
---
 platform/linux-generic/odp_schedule.c              | 26 +++++++++++++++-------
 platform/linux-generic/odp_schedule_sp.c           | 11 +++++++--
 .../validation/api/scheduler/scheduler.c           |  9 +++++++-
 3 files changed, 35 insertions(+), 11 deletions(-)

diff --git a/platform/linux-generic/odp_schedule.c 
b/platform/linux-generic/odp_schedule.c
index 78982d9..e24eec3 100644
--- a/platform/linux-generic/odp_schedule.c
+++ b/platform/linux-generic/odp_schedule.c
@@ -181,6 +181,7 @@ typedef struct {
        struct {
                char           name[ODP_SCHED_GROUP_NAME_LEN];
                odp_thrmask_t  mask;
+               int            allocated;
        } sched_grp[NUM_SCHED_GRPS];
 
        struct {
@@ -869,11 +870,19 @@ static odp_schedule_group_t schedule_group_create(const 
char *name,
        odp_spinlock_lock(&sched->grp_lock);
 
        for (i = SCHED_GROUP_NAMED; i < NUM_SCHED_GRPS; i++) {
-               if (sched->sched_grp[i].name[0] == 0) {
-                       strncpy(sched->sched_grp[i].name, name,
-                               ODP_SCHED_GROUP_NAME_LEN - 1);
+               if (!sched->sched_grp[i].allocated) {
+                       char *grp_name = sched->sched_grp[i].name;
+
+                       if (name == NULL) {
+                               grp_name[0] = 0;
+                       } else {
+                               strncpy(grp_name, name,
+                                       ODP_SCHED_GROUP_NAME_LEN - 1);
+                               grp_name[ODP_SCHED_GROUP_NAME_LEN - 1] = 0;
+                       }
                        odp_thrmask_copy(&sched->sched_grp[i].mask, mask);
                        group = (odp_schedule_group_t)i;
+                       sched->sched_grp[i].allocated = 1;
                        break;
                }
        }
@@ -889,10 +898,11 @@ static int schedule_group_destroy(odp_schedule_group_t 
group)
        odp_spinlock_lock(&sched->grp_lock);
 
        if (group < NUM_SCHED_GRPS && group >= SCHED_GROUP_NAMED &&
-           sched->sched_grp[group].name[0] != 0) {
+           sched->sched_grp[group].allocated) {
                odp_thrmask_zero(&sched->sched_grp[group].mask);
                memset(sched->sched_grp[group].name, 0,
                       ODP_SCHED_GROUP_NAME_LEN);
+               sched->sched_grp[group].allocated = 0;
                ret = 0;
        } else {
                ret = -1;
@@ -928,7 +938,7 @@ static int schedule_group_join(odp_schedule_group_t group,
        odp_spinlock_lock(&sched->grp_lock);
 
        if (group < NUM_SCHED_GRPS && group >= SCHED_GROUP_NAMED &&
-           sched->sched_grp[group].name[0] != 0) {
+           sched->sched_grp[group].allocated) {
                odp_thrmask_or(&sched->sched_grp[group].mask,
                               &sched->sched_grp[group].mask,
                               mask);
@@ -949,7 +959,7 @@ static int schedule_group_leave(odp_schedule_group_t group,
        odp_spinlock_lock(&sched->grp_lock);
 
        if (group < NUM_SCHED_GRPS && group >= SCHED_GROUP_NAMED &&
-           sched->sched_grp[group].name[0] != 0) {
+           sched->sched_grp[group].allocated) {
                odp_thrmask_t leavemask;
 
                odp_thrmask_xor(&leavemask, mask, &sched->mask_all);
@@ -973,7 +983,7 @@ static int schedule_group_thrmask(odp_schedule_group_t 
group,
        odp_spinlock_lock(&sched->grp_lock);
 
        if (group < NUM_SCHED_GRPS && group >= SCHED_GROUP_NAMED &&
-           sched->sched_grp[group].name[0] != 0) {
+           sched->sched_grp[group].allocated) {
                *thrmask = sched->sched_grp[group].mask;
                ret = 0;
        } else {
@@ -992,7 +1002,7 @@ static int schedule_group_info(odp_schedule_group_t group,
        odp_spinlock_lock(&sched->grp_lock);
 
        if (group < NUM_SCHED_GRPS && group >= SCHED_GROUP_NAMED &&
-           sched->sched_grp[group].name[0] != 0) {
+           sched->sched_grp[group].allocated) {
                info->name    = sched->sched_grp[group].name;
                info->thrmask = sched->sched_grp[group].mask;
                ret = 0;
diff --git a/platform/linux-generic/odp_schedule_sp.c 
b/platform/linux-generic/odp_schedule_sp.c
index 2e28aa4..b7b1de4 100644
--- a/platform/linux-generic/odp_schedule_sp.c
+++ b/platform/linux-generic/odp_schedule_sp.c
@@ -501,8 +501,15 @@ static odp_schedule_group_t schedule_group_create(const 
char *name,
 
        for (i = NUM_STATIC_GROUP; i < NUM_GROUP; i++) {
                if (!sched_group->s.group[i].allocated) {
-                       strncpy(sched_group->s.group[i].name, name,
-                               ODP_SCHED_GROUP_NAME_LEN);
+                       char *grp_name = sched_group->s.group[i].name;
+
+                       if (name == NULL) {
+                               grp_name[0] = 0;
+                       } else {
+                               strncpy(grp_name, name,
+                                       ODP_SCHED_GROUP_NAME_LEN - 1);
+                               grp_name[ODP_SCHED_GROUP_NAME_LEN - 1] = 0;
+                       }
                        odp_thrmask_copy(&sched_group->s.group[i].mask,
                                         thrmask);
                        sched_group->s.group[i].allocated = 1;
diff --git a/test/common_plat/validation/api/scheduler/scheduler.c 
b/test/common_plat/validation/api/scheduler/scheduler.c
index 919cfb6..dd3f6cd 100644
--- a/test/common_plat/validation/api/scheduler/scheduler.c
+++ b/test/common_plat/validation/api/scheduler/scheduler.c
@@ -273,7 +273,7 @@ void scheduler_test_groups(void)
                                      ODP_SCHED_SYNC_ORDERED};
        int thr_id = odp_thread_id();
        odp_thrmask_t zeromask, mymask, testmask;
-       odp_schedule_group_t mygrp1, mygrp2, lookup;
+       odp_schedule_group_t mygrp1, mygrp2, null_grp, lookup;
        odp_schedule_group_info_t info;
 
        odp_thrmask_zero(&zeromask);
@@ -327,6 +327,10 @@ void scheduler_test_groups(void)
        CU_ASSERT(rc == 0);
        CU_ASSERT(!odp_thrmask_isset(&testmask, thr_id));
 
+       /* Create group with no name */
+       null_grp = odp_schedule_group_create(NULL, &zeromask);
+       CU_ASSERT(null_grp != ODP_SCHED_GROUP_INVALID);
+
        /* We shouldn't be able to find our second group before creating it */
        lookup = odp_schedule_group_lookup("Test Group 2");
        CU_ASSERT(lookup == ODP_SCHED_GROUP_INVALID);
@@ -338,6 +342,9 @@ void scheduler_test_groups(void)
        lookup = odp_schedule_group_lookup("Test Group 2");
        CU_ASSERT(lookup == mygrp2);
 
+       /* Destroy group with no name */
+       CU_ASSERT_FATAL(odp_schedule_group_destroy(null_grp) == 0);
+
        /* Verify we're not part of it */
        rc = odp_schedule_group_thrmask(mygrp2, &testmask);
        CU_ASSERT(rc == 0);
-- 
2.7.4

Reply via email to