summaryrefslogtreecommitdiffstats
path: root/testsuites/sptests/spfreechain01/init.c
blob: 8f5e10f28d67ee1a2cc4c65e161e9790992ffd32 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
/*
 * Copyright (c) 2013 Zhongwei Yao.
 *
 *  The license and distribution terms for this file may be
 *  found in the file LICENSE in this distribution or at
 *  http://www.rtems.org/license/LICENSE.
 */

#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include <tmacros.h>
#include <rtems/score/chainimpl.h>
#include <rtems/score/freechain.h>
#include <rtems/score/wkspace.h>
#include <rtems/malloc.h>

const char rtems_test_name[] = "SPFREECHAIN 1";

/* forward declarations to avoid warnings */
rtems_task Init(rtems_task_argument argument);
bool my_freechain_extend_with_nothing( Freechain_Control *freechain );
bool my_freechain_extend_heap( Freechain_Control *freechain );
bool my_freechain_extend_workspace( Freechain_Control *freechain );
void my_freechain_init_heap( Freechain_Control *freechain );
void my_freechain_init_workspace( Freechain_Control *freechain );

typedef struct {
  Freechain_Control super_fc;
  size_t bump_count;
} MyFreechain;

typedef struct {
  Chain_Node ch_node;
  int x;
} test_node;

bool my_freechain_extend_with_nothing( Freechain_Control *freechain )
{
    return NULL;
}

/* user defined extend handle, it allocates memory on heap. */
bool my_freechain_extend_heap( Freechain_Control *freechain )
{
  MyFreechain *self = (MyFreechain *)freechain;
  size_t node_size = sizeof(test_node);
  size_t size = self->bump_count * node_size;
  int i;
  test_node *nodes = malloc(size);

  if (!nodes) {
    printf( "INIT - Unable to allocate free chain of size: %zd\n", size );
    return NULL;
  }

  puts( "INIT - Allocate node from heap in user defined freechain extend"
        " - OK" );
  for ( i = 0; i < self->bump_count; i++ ) {
      _Freechain_Put(freechain,
                          nodes + i);
  }
  return true;
}

/* user defined extend handle, it allocates memory on workspace. */
bool my_freechain_extend_workspace( Freechain_Control *freechain )
{
  MyFreechain *self = (MyFreechain *)freechain;
  size_t node_size = sizeof(test_node);
  size_t size = self->bump_count * node_size;
  int i;
  test_node *nodes = _Workspace_Allocate(size);

  if (!nodes) {
    printf( "INIT - Unable to allocate free chain of size: %zd\n", size );
    return NULL;
  }

  puts( "INIT - Allocate node from workspace in user defined freechain extend"
        " - OK" );

  for ( i = 0; i < self->bump_count; i++ ) {
      _Freechain_Put(freechain,
                          nodes + i);
  }
  return true;
}

void my_freechain_init_heap( Freechain_Control *freechain )
{
  MyFreechain *self = (MyFreechain *)freechain;
  self->bump_count = 5;
  size_t size = self->bump_count * sizeof(test_node);
  test_node *nodes = malloc(size);

  _Chain_Initialize(
    &freechain->Freechain,
    nodes,
    self->bump_count,
    sizeof(test_node)
    );
}

void my_freechain_init_workspace( Freechain_Control *freechain )
{
  MyFreechain *self = (MyFreechain *)freechain;
  self->bump_count = 7;
  size_t size = self->bump_count * sizeof(test_node);
  test_node *nodes = _Workspace_Allocate(size);

  _Chain_Initialize(
    &freechain->Freechain,
    nodes,
    self->bump_count,
    sizeof(test_node)
    );
}

rtems_task Init(
  rtems_task_argument ignored
                )
{
    TEST_BEGIN();

    test_node *test_node_p;
    MyFreechain myfc;
    Freechain_Control *fc_p = (Freechain_Control *)&myfc;
    int i;

    /* check whether freechain put and get works correctly*/
    _Freechain_Initialize(fc_p,
                          &my_freechain_extend_with_nothing);
    my_freechain_init_heap(fc_p);

    puts( "INIT - Get node from freechain - OK" );
    test_node_p = (test_node *)_Freechain_Get(fc_p);
    test_node_p->x = 1;

    puts( "INIT - Put node back to freechain - OK" );
    _Freechain_Put(fc_p, (void *)test_node_p);

    puts( "INIT - Verify freechain node put and get - OK" );
    test_node_p = (test_node *)_Freechain_Get(fc_p);
    if(test_node_p->x != 1) {
      puts( "INIT - ERROR ON FREECHAIN GET AND PUT" );
      rtems_test_exit(0);
    }

    /* check whether freechain extend handle on heap works correctly */
    _Freechain_Initialize(fc_p,
                          &my_freechain_extend_heap);
    my_freechain_init_heap(fc_p);

    puts( "INIT - Get more than intialized nodes from freechain on heap - OK" );

    for ( i = 0; i < myfc.bump_count * 2; i++ ) {
        test_node_p = (test_node *)_Freechain_Get(fc_p);
        if (!test_node_p) {
            puts( "INIT - Get node from freechain failed - FAILED" );
            rtems_test_exit(0);
        }
    }

    /* check whether freechain extend handle in workspace works correctly */
    _Freechain_Initialize(fc_p,
                          &my_freechain_extend_workspace);
    my_freechain_init_workspace(fc_p);

    puts( "INIT - Get more than intialized nodes from freechain in workspace"
          " - OK" );

    for ( i = 0; i < myfc.bump_count * 2; i++ ) {
        test_node_p = (test_node *)_Freechain_Get(fc_p);
        if (!test_node_p) {
            puts( "INIT - Get node from freechain failed - FAILED" );
            rtems_test_exit(0);
        }
    }

    TEST_END();
    rtems_test_exit(0);
}

/* configuration information */

#define CONFIGURE_APPLICATION_NEEDS_CONSOLE_DRIVER
#define CONFIGURE_APPLICATION_DOES_NOT_NEED_CLOCK_DRIVER

#define CONFIGURE_MEMORY_OVERHEAD sizeof(test_node)
#define CONFIGURE_INITIAL_EXTENSIONS RTEMS_TEST_INITIAL_EXTENSION

#define CONFIGURE_RTEMS_INIT_TASKS_TABLE
#define CONFIGURE_MAXIMUM_TASKS 1

#define CONFIGURE_INIT
#include <rtems/confdefs.h>

/* global variables */