• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

nasa / trick / 16919458345

12 Aug 2025 07:57PM UTC coverage: 55.859% (-0.08%) from 55.938%
16919458345

push

github

web-flow
Updated to allow to use index [0] on regular pointer. (#1929)

* Updated to allow to use index [0] on regular pointer.

* Added support to check the array bounds that a regular pointer points to.

* Updated to handle the pointer that doesn't point to array.

3 of 36 new or added lines in 2 files covered. (8.33%)

4 existing lines in 2 files now uncovered.

12346 of 22102 relevant lines covered (55.86%)

252942.92 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

50.6
/trick_source/sim_services/MemoryManager/MemoryManager_ref_dim.cpp
1
#include <stdio.h>
2
#include <sys/types.h>
3
#include <string.h>
4
#include <sstream>
5

6
#include "trick/MemoryManager.hh"
7
#include "trick/vval.h"
8
#include "trick/attributes.h"
9
#include "trick/reference.h"
10
#include "trick/parameter_types.h"
11

12
/*
13
 Updates R, a reference to an arrayed object, to a reference to the indexed sub-element of that arrayed object.
14
*/
15
int Trick::MemoryManager::ref_dim( REF2* R, V_DATA* V) {
21,744✔
16

17
    int jj;
18
    int item_size;
19
    int index_value = vval_int(V);
21,744✔
20

21
    if (R->ref_type != REF_ADDRESS) {
21,744✔
22
        emitError("Attempt to index into a non-address reference is bogus in ref_dim.") ;
×
23
        return (1);
×
24
    }
25

26
    R->num_index_left--;
21,744✔
27
    if (R->num_index_left < 0) {
21,744✔
28
        /* if we have too many dimensions, flag an error */
29
        emitError("Too many dimensions in ref_dim.\n") ;
×
30
        return (TRICK_PARAMETER_ARRAY_SIZE);
×
31
    }
32

33
    /*Calculate the size of the items in this array. */
34
    item_size =  R->attr->size;
21,744✔
35
    for (jj = (R->attr->num_index - 1); jj > R->num_index; jj--) {
23,087✔
36
        if (R->attr->index[jj].size > 0) {
1,343✔
37
            item_size *= R->attr->index[jj].size;
635✔
38
        } else {
39
            item_size = sizeof(void *);
708✔
40
            R->pointer_present = 1 ;
708✔
41
        }
42
    }
43

44
    /* if current dimension is a constrained ... */
45
    if (R->attr->index[R->num_index].size != 0) {
21,744✔
46

47
        /* for constrained dimensions, we can check the validity of the index value */
48
        if (index_value >= R->attr->index[R->num_index].size || index_value < 0) {
21,632✔
49
            /* print out of bounds error message if MM debug_level is greater than 1 */
50
            if (debug_level > 1) {
3✔
51
                emitError("Memory Manager ERROR: Array index out of bounds.") ;
×
52
            }
53
            return (TRICK_PARAMETER_ARRAY_SIZE);
3✔
54
        }
55

56
    } else {
57

58
        /* for unconstrained dimensions, we can check that the index value is non-negative
59
           and that it is less than the size of the array */
60
        if (index_value >= (get_size(*(void**)(R->address))) || index_value < 0) {
112✔
61

NEW
62
            if (index_value >= 0 && get_size(*(void**)(R->address)) == 0) {
×
63
                // Special case (do nothing here):
64
                //   For regular pointers as an equivalent to ->
65
                //   For array pointers that are not yet allocated
66
                // If a pointer is not allocated regardless of regular pointer or array pointer, an error message will be emitted below
67
                //   However, if the pointer is already assigned to a valid address, the error message will NOT be emitted below
68
            } else {
69
                /* print out of bounds error message if MM debug_level is greater than 1 */
NEW
70
                if (debug_level > 1) {
×
NEW
71
                    std::stringstream message;
×
NEW
72
                    message << index_value << " is out of bounds for " << R->reference << " (size=" << get_size(*(void**)(R->address)) << ").";
×
NEW
73
                    emitError(message.str());
×
74
                }
NEW
75
                return (TRICK_PARAMETER_ARRAY_SIZE);
×
76
            }
77
        }
78

79
        R->pointer_present = 1 ;
112✔
80
        if ( R->create_add_path ) {
112✔
81
            ADDRESS_NODE * address_node ;
82

83
            address_node = new ADDRESS_NODE ;
112✔
84
            address_node->operator_ = AO_DEREFERENCE ;
112✔
85
            address_node->operand.address = NULL ;
112✔
86
            DLL_AddTail(address_node , R->address_path) ;
112✔
87
        }
88

89
        // Dereference the pointer.
90
        R->address = *(void**)R->address;
112✔
91
        if ( R->address == NULL) {
112✔
92
            std::stringstream message;
×
93
            message << "Reference (" << R->reference << ") address is NULL in ref_dim.";
×
94
            emitError(message.str());
×
95
            return(TRICK_PARAMETER_ADDRESS_NULL) ;
×
96
        }
97

98
        // Get allocation information for the address
99
        ALLOC_INFO *alloc_info = get_alloc_info_of(R->address);
112✔
100

101
        // Skip if allocation name is NULL
102
        if (alloc_info != NULL && alloc_info->name != NULL) {
112✔
103
            // Get the reference name from the address that R points if exists and contains & at front
104
            // Otherwise, the pointer is not assigned to anything else rather itself is allocated
NEW
105
            std::string ref_name = ref_name_from_address(R->address);
×
NEW
106
            if (!ref_name.empty() && ref_name.front() == '&') {
×
NEW
107
                ref_name = ref_name.substr(1);
×
108

109
                // Get the reference attributes for what the pointer points to
NEW
110
                REF2 *ref2 = ref_attributes((char*)ref_name.c_str());
×
111

112
                // Check if the reference that the pointer points to is valid. Return error if not.
NEW
113
                if (ref2 == NULL) {
×
NEW
114
                    std::stringstream message;
×
NEW
115
                    message << "Reference (" << R->reference << ") is not allocated in ref_dim.";
×
NEW
116
                    emitError(message.str());
×
NEW
117
                    return(TRICK_PARAMETER_ADDRESS_NULL);
×
118
                }
119

120
                // Only check bounds if ref2 is array-ed
NEW
121
                if (ref2->num_index > 0) {
×
122
                    // Check if the pointer points to a static array or a dynamic array and if array index is out of bounds
NEW
123
                    if (ref2->attr && ref2->attr->index[ref2->attr->num_index-1].size != 0) { // Static array case
×
124
                        // Check if the index is out of bounds if the pointer points to a static array
NEW
125
                        if (index_value >= ref2->attr->index[ref2->attr->num_index-1].size || index_value < 0) {
×
126
                            /* print out of bounds error message if MM debug_level is greater than 1 */
NEW
127
                            if (debug_level > 1) {
×
NEW
128
                                emitError("Memory Manager ERROR: Array index out of bounds.") ;
×
129
                            }
NEW
130
                            free(ref2);
×
NEW
131
                            return (TRICK_PARAMETER_ARRAY_SIZE);
×
132
                        }
133
                    } else { // Dynamic array case
134
                        // Check if the index is out of bounds if the pointer points to a dynamic array
NEW
135
                        if (index_value >= (get_size(*(void**)(R->address)))) {
×
136
                            /* print out of bounds error message if MM debug_level is greater than 1 */
NEW
137
                            if (debug_level > 1) {
×
NEW
138
                                std::stringstream message;
×
NEW
139
                                message << index_value << " is out of bounds for " << R->reference << " (size=" << get_size(*(void**)(R->address)) << ").";
×
NEW
140
                                emitError(message.str());
×
141
                            }
NEW
142
                            free(ref2);
×
NEW
143
                            return (TRICK_PARAMETER_ARRAY_SIZE);
×
144
                        }
145
                    }
146
                }
147
            } // if (!ref_name.empty() && ref_name.front() == '&') {
148
        } // if (alloc_info->name != NULL) {
149
    } // if (R->attr->index[R->num_index].size != 0) {
150

151
    if ( R->create_add_path ) {
21,741✔
152

153
        ADDRESS_NODE * address_node ;
154

155
        if ( index_value > 0 ) {
9,798✔
156
            address_node = (ADDRESS_NODE *)DLL_GetAt(DLL_GetTailPosition(R->address_path), R->address_path) ;
9,191✔
157
            switch ( address_node->operator_ ) {
9,191✔
158
                case AO_ADDRESS:
9,079✔
159
                    address_node->operand.address = (void *)((char *)address_node->operand.address +  index_value * item_size) ;
9,079✔
160
                    break ;
9,079✔
161
                case AO_DEREFERENCE:
112✔
162
                    address_node = new ADDRESS_NODE ;
112✔
163
                    address_node->operator_ = AO_OFFSET ;
112✔
164
                    address_node->operand.offset = index_value * item_size ;
112✔
165
                    DLL_AddTail(address_node , R->address_path) ;
112✔
166
                    break ;
112✔
167
                case AO_OFFSET:
×
168
                    address_node->operand.offset += index_value * item_size ;
×
169
                    break ;
×
170
            }
171
        }
172
    }
173

174
    R->address =  (void*)((char*)R->address + index_value * item_size);
21,741✔
175
    R->num_index++;
21,741✔
176

177
    return (TRICK_NO_ERROR);
21,741✔
178
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc