/* Copyright (C) 2021-2026 Free Software Foundation, Inc. Contributed by Oracle. This file is part of GNU Binutils. 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 3, 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, 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */ #include "config.h"#include <ctype.h> #include "util.h"#include "DbeSession.h"#include "Application.h"#include "Experiment.h"#include "Exp_Layout.h"#include "MetricList.h"#include "MemObject.h"#include "PathTree.h"#include "DbeView.h"#include "Metric.h"#include "MemorySpace.h"#include "Table.h"#include "IndexObject.h" MemObjType_t::MemObjType_t (){ type = -1; name = NULL; index_expr = NULL; machmodel = NULL; mnemonic = 0; short_description = NULL; long_description = NULL;} MemObjType_t::~MemObjType_t (){ free (name); free (index_expr); free (machmodel); free (short_description); free (long_description);} MemorySpace::MemorySpace (DbeView *_dbev, int _mstype){ char *mname; dbev = _dbev; phaseIdx = -1; // set up the MemoryObject information objs = new HashMap<uint64_t, MemObj*>; mstype = _mstype; msindex_exp = NULL; msname = NULL; msindex_exp_str = NULL; // find the memory space in the table MemObjType_t *mot = findMemSpaceByIndex (mstype); if (mot) { msname = dbe_strdup (mot->name); if (mot->index_expr != NULL) { msindex_exp_str = dbe_strdup (mot->index_expr); msindex_exp = dbeSession->ql_parse (msindex_exp_str); if (msindex_exp == NULL) // this was checked when the definition was created abort (); } } // create the Total and Unknown objects mname = dbe_strdup (NTXT ("<Total>")); total_memobj = createMemObject ((uint64_t) - 2, mname); mname = dbe_strdup (GTXT ("<Unknown>")); unk_memobj = createMemObject ((uint64_t) - 1, mname); hist_data_all = NULL; selected_mo_index = (uint64_t) - 3; sel_ind = -1;} MemorySpace::~MemorySpace (){ reset (); delete objs; free (msname); free (msindex_exp); free (msindex_exp_str);} voidMemorySpace::reset (){ if (hist_data_all != NULL) { delete hist_data_all; hist_data_all = NULL; } // do not clear the selected object's index // selected_mo_index = (uint64_t)-3; // destroy any existing objects, but keep the vector // Now that we have a hashmap, which has its own vector, // safe to delete and reallocate delete objs; objs = new HashMap<uint64_t, MemObj*>;} // find a memory object by its memory-object indexintMemorySpace::findMemObject (uint64_t indx){ int index; Hist_data::HistItem *hi; if (indx == (uint64_t) - 3) return -1; Vec_loop (Hist_data::HistItem *, hist_data_all->hist_items, index, hi) { if (((uint64_t) ((MemObj *) hi->obj)->id) == indx) return index; } // object does not exist; filter change eliminated it, for example return -1;} // find the object referenced in the packetMemObj *MemorySpace::lookupMemObject (Experiment *exp, DataView *packets, long i){ uint64_t idx; uint64_t va = (uint64_t) packets->getLongValue (PROP_VADDR, i); if (va == ABS_UNSUPPORTED) // return NULL, to ignore the record return NULL; if (va < ABS_CODE_RANGE) // The va is not valid, rather, it's an error code // return the <Unknown> object return unk_memobj; Expression::Context ctx (dbev, exp, packets, i); idx = msindex_exp->eval (&ctx); if (idx == (uint64_t) - 1) return unk_memobj; // do a binary search for the memory object MemObj *res = objs->get (idx); if (res == NULL) { res = createMemObject (idx, NULL); objs->put (idx, res); } else return res; // recompute range if (idx < idx_min) idx_min = idx; if (idx > idx_max) idx_max = idx; return res;} MemObj *MemorySpace::createMemObject (uint64_t index, char *moname){ MemObj *res; char *name; if (moname != NULL) { res = new MemObj (index, moname); return res; } // Custom memory objects // The memory_page_size is defined in the machine model file such // as ./machinemodels/t4.ermm. // Most users prefer to look at the hexadecimal version of virtual // addresses. Display only the hexadecimal version of virtual addresses // for all machine model views with an exception of virtual page size. if (dbe_strcmp (msname, NTXT ("Memory_page_size")) == 0) name = dbe_sprintf (NTXT ("%s 0x%16.16llx (%llu)"), msname, (long long) index, (unsigned long long) index); else if (dbe_strcmp (msname, NTXT ("Memory_in_home_lgrp")) == 0) name = dbe_sprintf (NTXT ("%s: %s"), msname, index == 1 ? GTXT ("True") : index == 0 ? GTXT ("False") : GTXT ("<Unknown>")); else if (dbe_strcmp (msname, NTXT ("Memory_lgrp")) == 0) name = dbe_sprintf (NTXT ("%s %llu"), msname, (unsigned long long) index); else name = dbe_sprintf (NTXT ("%s 0x%16.16llx"), msname, (long long) index); res = new MemObj (index, name); return res;} static Vector<MemObjType_t*> dyn_memobj_vec;static Vector<MemObjType_t*> *dyn_memobj = &dyn_memobj_vec;static Vector<int> *ordlist; // Static function to get a vector of custom memory object definitions Vector<void*> *MemorySpace::getMemObjects (){ MemObjType_t *mot; int ii; int size = dyn_memobj->size (); Vector<int> *indx = new Vector<int>(size); Vector<char*> *name = new Vector<char*>(size); Vector<char> *mnemonic = new Vector<char>(size); Vector<char*> *formula = new Vector<char*>(size); Vector<char*> *machmodel = new Vector<char*>(size); Vector<int> *order = new Vector<int>(size); Vector<char*> *sdesc = new Vector<char*>(size); Vector<char*> *ldesc = new Vector<char*>(size); if (size > 0) { Vec_loop (MemObjType_t *, dyn_memobj, ii, mot) { indx->store (ii, mot->type); order->store (ii, ii); name->store (ii, dbe_strdup (mot->name)); formula->store (ii, dbe_strdup (mot->index_expr)); mnemonic->store (ii, mot->mnemonic); sdesc->store (ii, mot->short_description == NULL ? NULL : dbe_strdup (mot->short_description)); ldesc->store (ii, mot->long_description == NULL ? NULL : dbe_strdup (mot->long_description)); if (mot->machmodel == NULL) machmodel->store (ii, NULL); else machmodel->store (ii, dbe_strdup (mot->machmodel)); } } Vector<void*> *res = new Vector<void*>(8); res->store (0, indx); res->store (1, name); res->store (2, mnemonic); res->store (3, formula); res->store (4, machmodel); res->store (5, order); res->store (6, sdesc); res->store (7, ldesc); return (res);} // Static function to set order of memory object tabsvoidMemorySpace::set_MemTabOrder (Vector<int> *orders){ int size = orders->size (); ordlist = new Vector<int>(size); for (int i = 0; i < size; i++) ordlist->store (i, orders->fetch (i));} // Static function to define a new memory object typechar *MemorySpace::mobj_define (char *mname, char *mindex_exp, char *_machmodel, char *short_description, char *long_description){ MemObjType_t *mot; if (mname == NULL) return dbe_strdup (GTXT ("No memory object name has been specified.")); if (isalpha ((int) (mname[0])) == 0) return dbe_sprintf (GTXT ("Memory Object type name %s does not begin with an alphabetic character"), mname); char *p = mname; while (*p != 0) { if (isalnum ((int) (*p)) == 0 && *p != '_') return dbe_sprintf (GTXT ("Memory Object type name %s contains a non-alphanumeric character"), mname); p++; } mot = findMemSpaceByName (mname); if (mot != NULL) { if (strcmp (mot->index_expr, mindex_exp) == 0) // It's a redefinition, but the new definition is the same return NULL; return dbe_sprintf (GTXT ("Memory/Index Object type name %s is already defined"), mname); } // make sure the name is not in use if (dbeSession->findIndexSpaceByName (mname) >= 0) return dbe_sprintf (GTXT ("Memory/Index Object type name %s is already defined"), mname); if (mindex_exp == NULL || *mindex_exp == 0) return dbe_strdup (GTXT ("No index-expr has been specified.")); // verify that the index expression parses correctly Expression *e = dbeSession->ql_parse (mindex_exp); if (e == NULL) return dbe_sprintf (GTXT ("Memory Object index expression is invalid: %s"), mindex_exp); delete e; // It's OK, create the new table entry char *s = dbeSession->indxobj_define (mname, NULL, mindex_exp, short_description, long_description); if (s) return s; IndexObjType_t *indObj = dbeSession->findIndexSpace (mname); mot = new MemObjType_t; mot->type = indObj->type; indObj->memObj = mot; mot->name = dbe_strdup (mname); mot->index_expr = dbe_strdup (mindex_exp); mot->mnemonic = MemorySpace::pickMnemonic (mname); mot->machmodel = dbe_strdup (_machmodel); mot->short_description = dbe_strdup (short_description); mot->long_description = dbe_strdup (long_description); // add it to the list dyn_memobj->append (mot); // tell the session if (dbeSession != NULL) dbeSession->mobj_define (mot); return NULL;} // Static function to delete a new memory object type char *MemorySpace::mobj_delete (char *mname){ if (mname == NULL) return dbe_strdup (GTXT ("No memory object name has been specified.\n")); // search the dynamic types for (long idx = 0, sz = VecSize (dyn_memobj); idx < sz; idx++) { MemObjType_t *mt = dyn_memobj->get (idx); if (strcasecmp (mt->name, mname) == 0) { // delete it from the vector mt = dyn_memobj->remove (idx); delete mt; dbeSession->removeIndexSpaceByName (mname); return NULL; } } return dbe_sprintf (GTXT ("Memory object `%s' is not defined.\n"), mname);} // Static function to get a list of memory object names from a machine model Vector <char*> *MemorySpace::getMachineModelMemObjs (char *mname){ Vector <char *> *ret = new Vector <char *> (); if (mname == NULL) return ret; // search the memory objects int idx; MemObjType_t *mt; Vec_loop (MemObjType_t*, dyn_memobj, idx, mt) { if (mt->machmodel != NULL && strcmp (mt->machmodel, mname) == 0) { char *n = dbe_strdup (mt->name); ret->append (n); } } return ret;} charMemorySpace::pickMnemonic (char *name){ return name[0];} voidMemorySpace::get_filter_keywords (Vector <void*> *res){ Vector <char*> *kwCategory = (Vector<char*>*) res->fetch (0); Vector <char*> *kwCategoryI18N = (Vector<char*>*) res->fetch (1); Vector <char*> *kwDataType = (Vector<char*>*) res->fetch (2); Vector <char*> *kwKeyword = (Vector<char*>*) res->fetch (3); Vector <char*> *kwFormula = (Vector<char*>*) res->fetch (4); Vector <char*> *kwDescription = (Vector<char*>*) res->fetch (5); Vector <void*> *kwEnumDescs = (Vector<void*>*) res->fetch (6); char *vtypeNames[] = VTYPE_TYPE_NAMES; for (int i = 0, sz = dyn_memobj ? dyn_memobj->size () : 0; i < sz; i++) { MemObjType_t *obj = dyn_memobj->fetch (i); kwCategory->append (dbe_strdup (NTXT ("FK_MEMOBJ"))); kwCategoryI18N->append (dbe_strdup (GTXT ("Memory Object Definitions"))); kwDataType->append (dbe_strdup (vtypeNames[TYPE_INT64])); kwKeyword->append (dbe_strdup (obj->name)); kwFormula->append (dbe_strdup (obj->index_expr)); kwDescription->append (NULL); kwEnumDescs->append (NULL); }} MemObjType_t *MemorySpace::findMemSpaceByName (const char *mname){ int idx; MemObjType_t *mt; // search the dynamic types Vec_loop (MemObjType_t*, dyn_memobj, idx, mt) { if (strcasecmp (mt->name, mname) == 0) return mt; } return NULL;} MemObjType_t *MemorySpace::findMemSpaceByIndex (int index){ int idx; MemObjType_t *mt; // search the dynamic types Vec_loop (MemObjType_t*, dyn_memobj, idx, mt) { if (mt->type == index) return mt; } return NULL;}
/* Copyright (C) 2021-2026 Free Software Foundation, Inc.
Contributed by Oracle.
This file is part of GNU Binutils.
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 3, 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, 51 Franklin Street - Fifth Floor, Boston,
MA 02110-1301, USA. */
#include "config.h"
#include <ctype.h>
#include "util.h"
#include "DbeSession.h"
#include "Application.h"
#include "Experiment.h"
#include "Exp_Layout.h"
#include "MetricList.h"
#include "MemObject.h"
#include "PathTree.h"
#include "DbeView.h"
#include "Metric.h"
#include "MemorySpace.h"
#include "Table.h"
#include "IndexObject.h"
MemObjType_t::MemObjType_t ()
{
type = -1;
name = NULL;
index_expr = NULL;
machmodel = NULL;
mnemonic = 0;
short_description = NULL;
long_description = NULL;
}
MemObjType_t::~MemObjType_t ()
{
free (name);
free (index_expr);
free (machmodel);
free (short_description);
free (long_description);
}
MemorySpace::MemorySpace (DbeView *_dbev, int _mstype)
{
char *mname;
dbev = _dbev;
phaseIdx = -1;
// set up the MemoryObject information
objs = new HashMap<uint64_t, MemObj*>;
mstype = _mstype;
msindex_exp = NULL;
msname = NULL;
msindex_exp_str = NULL;
// find the memory space in the table
MemObjType_t *mot = findMemSpaceByIndex (mstype);
if (mot)
{
msname = dbe_strdup (mot->name);
if (mot->index_expr != NULL)
{
msindex_exp_str = dbe_strdup (mot->index_expr);
msindex_exp = dbeSession->ql_parse (msindex_exp_str);
if (msindex_exp == NULL)
// this was checked when the definition was created
abort ();
}
}
// create the Total and Unknown objects
mname = dbe_strdup (NTXT ("<Total>"));
total_memobj = createMemObject ((uint64_t) - 2, mname);
mname = dbe_strdup (GTXT ("<Unknown>"));
unk_memobj = createMemObject ((uint64_t) - 1, mname);
hist_data_all = NULL;
selected_mo_index = (uint64_t) - 3;
sel_ind = -1;
}
MemorySpace::~MemorySpace ()
{
reset ();
delete objs;
free (msname);
free (msindex_exp);
free (msindex_exp_str);
}
void
MemorySpace::reset ()
{
if (hist_data_all != NULL)
{
delete hist_data_all;
hist_data_all = NULL;
}
// do not clear the selected object's index
// selected_mo_index = (uint64_t)-3;
// destroy any existing objects, but keep the vector
// Now that we have a hashmap, which has its own vector,
// safe to delete and reallocate
delete objs;
objs = new HashMap<uint64_t, MemObj*>;
}
// find a memory object by its memory-object index
int
MemorySpace::findMemObject (uint64_t indx)
{
int index;
Hist_data::HistItem *hi;
if (indx == (uint64_t) - 3)
return -1;
Vec_loop (Hist_data::HistItem *, hist_data_all->hist_items, index, hi)
{
if (((uint64_t) ((MemObj *) hi->obj)->id) == indx)
return index;
}
// object does not exist; filter change eliminated it, for example
return -1;
}
// find the object referenced in the packet
MemObj *
MemorySpace::lookupMemObject (Experiment *exp, DataView *packets, long i)
{
uint64_t idx;
uint64_t va = (uint64_t) packets->getLongValue (PROP_VADDR, i);
if (va == ABS_UNSUPPORTED)
// return NULL, to ignore the record
return NULL;
if (va < ABS_CODE_RANGE)
// The va is not valid, rather, it's an error code
// return the <Unknown> object
return unk_memobj;
Expression::Context ctx (dbev, exp, packets, i);
idx = msindex_exp->eval (&ctx);
if (idx == (uint64_t) - 1)
return unk_memobj;
// do a binary search for the memory object
MemObj *res = objs->get (idx);
if (res == NULL)
{
res = createMemObject (idx, NULL);
objs->put (idx, res);
}
else
return res;
// recompute range
if (idx < idx_min)
idx_min = idx;
if (idx > idx_max)
idx_max = idx;
return res;
}
MemObj *
MemorySpace::createMemObject (uint64_t index, char *moname)
{
MemObj *res;
char *name;
if (moname != NULL)
{
res = new MemObj (index, moname);
return res;
}
// Custom memory objects
// The memory_page_size is defined in the machine model file such
// as ./machinemodels/t4.ermm.
// Most users prefer to look at the hexadecimal version of virtual
// addresses. Display only the hexadecimal version of virtual addresses
// for all machine model views with an exception of virtual page size.
if (dbe_strcmp (msname, NTXT ("Memory_page_size")) == 0)
name = dbe_sprintf (NTXT ("%s 0x%16.16llx (%llu)"), msname,
(long long) index, (unsigned long long) index);
else if (dbe_strcmp (msname, NTXT ("Memory_in_home_lgrp")) == 0)
name = dbe_sprintf (NTXT ("%s: %s"), msname,
index == 1 ? GTXT ("True") : index == 0 ? GTXT ("False")
: GTXT ("<Unknown>"));
else if (dbe_strcmp (msname, NTXT ("Memory_lgrp")) == 0)
name = dbe_sprintf (NTXT ("%s %llu"), msname, (unsigned long long) index);
else
name = dbe_sprintf (NTXT ("%s 0x%16.16llx"), msname, (long long) index);
res = new MemObj (index, name);
return res;
}
static Vector<MemObjType_t*> dyn_memobj_vec;
static Vector<MemObjType_t*> *dyn_memobj = &dyn_memobj_vec;
static Vector<int> *ordlist;
// Static function to get a vector of custom memory object definitions
Vector<void*> *
MemorySpace::getMemObjects ()
{
MemObjType_t *mot;
int ii;
int size = dyn_memobj->size ();
Vector<int> *indx = new Vector<int>(size);
Vector<char*> *name = new Vector<char*>(size);
Vector<char> *mnemonic = new Vector<char>(size);
Vector<char*> *formula = new Vector<char*>(size);
Vector<char*> *machmodel = new Vector<char*>(size);
Vector<int> *order = new Vector<int>(size);
Vector<char*> *sdesc = new Vector<char*>(size);
Vector<char*> *ldesc = new Vector<char*>(size);
if (size > 0)
{
Vec_loop (MemObjType_t *, dyn_memobj, ii, mot)
{
indx->store (ii, mot->type);
order->store (ii, ii);
name->store (ii, dbe_strdup (mot->name));
formula->store (ii, dbe_strdup (mot->index_expr));
mnemonic->store (ii, mot->mnemonic);
sdesc->store (ii, mot->short_description == NULL ? NULL
: dbe_strdup (mot->short_description));
ldesc->store (ii, mot->long_description == NULL ? NULL
: dbe_strdup (mot->long_description));
if (mot->machmodel == NULL)
machmodel->store (ii, NULL);
else
machmodel->store (ii, dbe_strdup (mot->machmodel));
}
}
Vector<void*> *res = new Vector<void*>(8);
res->store (0, indx);
res->store (1, name);
res->store (2, mnemonic);
res->store (3, formula);
res->store (4, machmodel);
res->store (5, order);
res->store (6, sdesc);
res->store (7, ldesc);
return (res);
}
// Static function to set order of memory object tabs
void
MemorySpace::set_MemTabOrder (Vector<int> *orders)
{
int size = orders->size ();
ordlist = new Vector<int>(size);
for (int i = 0; i < size; i++)
ordlist->store (i, orders->fetch (i));
}
// Static function to define a new memory object type
char *
MemorySpace::mobj_define (char *mname, char *mindex_exp, char *_machmodel,
char *short_description, char *long_description)
{
MemObjType_t *mot;
if (mname == NULL)
return dbe_strdup (GTXT ("No memory object name has been specified."));
if (isalpha ((int) (mname[0])) == 0)
return dbe_sprintf (GTXT ("Memory Object type name %s does not begin with an alphabetic character"),
mname);
char *p = mname;
while (*p != 0)
{
if (isalnum ((int) (*p)) == 0 && *p != '_')
return dbe_sprintf (GTXT ("Memory Object type name %s contains a non-alphanumeric character"),
mname);
p++;
}
mot = findMemSpaceByName (mname);
if (mot != NULL)
{
if (strcmp (mot->index_expr, mindex_exp) == 0)
// It's a redefinition, but the new definition is the same
return NULL;
return dbe_sprintf (GTXT ("Memory/Index Object type name %s is already defined"),
mname);
}
// make sure the name is not in use
if (dbeSession->findIndexSpaceByName (mname) >= 0)
return dbe_sprintf (GTXT ("Memory/Index Object type name %s is already defined"),
mname);
if (mindex_exp == NULL || *mindex_exp == 0)
return dbe_strdup (GTXT ("No index-expr has been specified."));
// verify that the index expression parses correctly
Expression *e = dbeSession->ql_parse (mindex_exp);
if (e == NULL)
return dbe_sprintf (GTXT ("Memory Object index expression is invalid: %s"),
mindex_exp);
delete e;
// It's OK, create the new table entry
char *s = dbeSession->indxobj_define (mname, NULL, mindex_exp,
short_description, long_description);
if (s)
return s;
IndexObjType_t *indObj = dbeSession->findIndexSpace (mname);
mot = new MemObjType_t;
mot->type = indObj->type;
indObj->memObj = mot;
mot->name = dbe_strdup (mname);
mot->index_expr = dbe_strdup (mindex_exp);
mot->mnemonic = MemorySpace::pickMnemonic (mname);
mot->machmodel = dbe_strdup (_machmodel);
mot->short_description = dbe_strdup (short_description);
mot->long_description = dbe_strdup (long_description);
// add it to the list
dyn_memobj->append (mot);
// tell the session
if (dbeSession != NULL)
dbeSession->mobj_define (mot);
return NULL;
}
// Static function to delete a new memory object type
char *
MemorySpace::mobj_delete (char *mname)
{
if (mname == NULL)
return dbe_strdup (GTXT ("No memory object name has been specified.\n"));
// search the dynamic types
for (long idx = 0, sz = VecSize (dyn_memobj); idx < sz; idx++)
{
MemObjType_t *mt = dyn_memobj->get (idx);
if (strcasecmp (mt->name, mname) == 0)
{
// delete it from the vector
mt = dyn_memobj->remove (idx);
delete mt;
dbeSession->removeIndexSpaceByName (mname);
return NULL;
}
}
return dbe_sprintf (GTXT ("Memory object `%s' is not defined.\n"), mname);
}
// Static function to get a list of memory object names from a machine model
Vector <char*> *
MemorySpace::getMachineModelMemObjs (char *mname)
{
Vector <char *> *ret = new Vector <char *> ();
if (mname == NULL)
return ret;
// search the memory objects
int idx;
MemObjType_t *mt;
Vec_loop (MemObjType_t*, dyn_memobj, idx, mt)
{
if (mt->machmodel != NULL && strcmp (mt->machmodel, mname) == 0)
{
char *n = dbe_strdup (mt->name);
ret->append (n);
}
}
return ret;
}
char
MemorySpace::pickMnemonic (char *name)
{
return name[0];
}
void
MemorySpace::get_filter_keywords (Vector <void*> *res)
{
Vector <char*> *kwCategory = (Vector<char*>*) res->fetch (0);
Vector <char*> *kwCategoryI18N = (Vector<char*>*) res->fetch (1);
Vector <char*> *kwDataType = (Vector<char*>*) res->fetch (2);
Vector <char*> *kwKeyword = (Vector<char*>*) res->fetch (3);
Vector <char*> *kwFormula = (Vector<char*>*) res->fetch (4);
Vector <char*> *kwDescription = (Vector<char*>*) res->fetch (5);
Vector <void*> *kwEnumDescs = (Vector<void*>*) res->fetch (6);
char *vtypeNames[] = VTYPE_TYPE_NAMES;
for (int i = 0, sz = dyn_memobj ? dyn_memobj->size () : 0; i < sz; i++)
{
MemObjType_t *obj = dyn_memobj->fetch (i);
kwCategory->append (dbe_strdup (NTXT ("FK_MEMOBJ")));
kwCategoryI18N->append (dbe_strdup (GTXT ("Memory Object Definitions")));
kwDataType->append (dbe_strdup (vtypeNames[TYPE_INT64]));
kwKeyword->append (dbe_strdup (obj->name));
kwFormula->append (dbe_strdup (obj->index_expr));
kwDescription->append (NULL);
kwEnumDescs->append (NULL);
}
}
MemObjType_t *
MemorySpace::findMemSpaceByName (const char *mname)
{
int idx;
MemObjType_t *mt;
// search the dynamic types
Vec_loop (MemObjType_t*, dyn_memobj, idx, mt)
{
if (strcasecmp (mt->name, mname) == 0)
return mt;
}
return NULL;
}
MemObjType_t *
MemorySpace::findMemSpaceByIndex (int index)
{
int idx;
MemObjType_t *mt;
// search the dynamic types
Vec_loop (MemObjType_t*, dyn_memobj, idx, mt)
{
if (mt->type == index)
return mt;
}
return NULL;
}