1 /**
2 * @file rm_dtb_util.c
3 *
4 * @brief
5 * This is the Resource Manager Resource List and Policy DTB parsing
6 * utility source
7 *
8 * \par
9 * ============================================================================
10 * @n (C) Copyright 2012-2015, Texas Instruments, Inc.
11 *
12 * Redistribution and use in source and binary forms, with or without
13 * modification, are permitted provided that the following conditions
14 * are met:
15 *
16 * Redistributions of source code must retain the above copyright
17 * notice, this list of conditions and the following disclaimer.
18 *
19 * Redistributions in binary form must reproduce the above copyright
20 * notice, this list of conditions and the following disclaimer in the
21 * documentation and/or other materials provided with the
22 * distribution.
23 *
24 * Neither the name of Texas Instruments Incorporated nor the names of
25 * its contributors may be used to endorse or promote products derived
26 * from this software without specific prior written permission.
27 *
28 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
29 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
30 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
31 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
32 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
33 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
34 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
35 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
36 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
37 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
38 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39 *
40 * \par
41 */
43 /* RM external API includes */
44 #include <ti/drv/rm/rm.h>
46 /* RM internal API includes */
47 #include <ti/drv/rm/include/rm_internal.h>
48 #include <ti/drv/rm/include/rm_dtb_utilloc.h>
50 /* RM OSAL layer */
51 #include <rm_osal.h>
53 /* LIBFDT includes */
54 #include <ti/drv/rm/util/libfdt/libfdt.h>
55 #include <ti/drv/rm/util/libfdt/libfdt_env.h>
57 /**********************************************************************
58 ************ Global Resource List (GRL) Parsing Globals **************
59 **********************************************************************/
61 /* Resource List Properties - These are the property values used
62 * by an application integrator to define the properties of resources
63 * listed in the Device Global Resource List (GRL) */
64 const char dtbUtilResRangeProp[] = "resource-range";
65 const char dtbUtilResLinuxAliasProp[] = "linux-dtb-alias";
66 const char dtbUtilResNsAssignmentProp[] = "ns-assignment";
68 /**********************************************************************
69 *********************** Policy Parsing Globals ***********************
70 **********************************************************************/
72 /* Policy Properties - These are the property values used
73 * by an application integrator to define the properties of resources
74 * listed in a Resource Manager Policy */
75 const char dtbUtilPolicyValidInstances[] = "valid-instances";
76 const char dtbUtilPolicyAssignments[] = "assignments";
77 const char dtbUtilPolicyCdAllocationSize[] = "cd-allocation-size";
78 const char dtbUtilPolicyAllocationAlignment[] = "allocation-alignment";
80 /**********************************************************************
81 ******************* Common DTB Parsing Functions *********************
82 **********************************************************************/
84 /* FUNCTION PURPOSE: Extracts ranges from a DTB
85 ***********************************************************************
86 * DESCRIPTION: Returns a list of ranges extracted from a DTB
87 * file. A range in the DTB is specified as <x y> where
88 * x is a base value and y is a length value. Ranges can
89 * be chained in the DTB with comma separation.
90 * Example:
91 * <0 10>,
92 * <20 100>,
93 * <200 100>;
94 * Results in a list of three ranges.
95 */
96 static Rm_ResourceRange *dtbUtilCommonExtractRange(const void *dtbDataPtr,
97 int32_t dtbDataLen)
98 {
99 uint32_t *dtbRangeData = (uint32_t *)dtbDataPtr;
100 Rm_ResourceRange *startRange = NULL;
101 Rm_ResourceRange *newRange = NULL;
102 Rm_ResourceRange *prevRange = NULL;
103 uint32_t i;
105 /* Ranges are stored in the DTB as a list of 32-bit words. The number of
106 * 32-bit words in the DTB ranges field should be even since ranges are
107 * specified in a base, lenth format. The DTB gives properties lengths in
108 * bytes so the length returned from the DTB should be a multiple of the
109 * number of bytes in two uint32_ts. */
110 if (dtbDataLen % (2 * sizeof(uint32_t))) {
111 return (NULL);
112 }
114 for (i = 0; i < (dtbDataLen / sizeof(uint32_t)); i+=2) {
115 newRange = (Rm_ResourceRange *) Rm_osalMalloc(sizeof(Rm_ResourceRange));
116 newRange->base = fdt32_to_cpu(dtbRangeData[i]);
117 newRange->length = fdt32_to_cpu(dtbRangeData[i+1]);
118 newRange->nextRange = NULL;
120 if (prevRange == NULL) {
121 startRange = newRange;
122 } else {
123 prevRange->nextRange = newRange;
124 }
125 prevRange = newRange;
126 }
127 return(startRange);
128 }
130 /* FUNCTION PURPOSE: Deletes a range list
131 ***********************************************************************
132 * DESCRIPTION: Frees the memory associated with a list of ranges
133 * that were extracted from a DTB.
134 */
135 static void dtbUtilCommonFreeRangeList(Rm_ResourceRange *rangeList)
136 {
137 Rm_ResourceRange *nextRange;
139 while (rangeList) {
140 nextRange = rangeList->nextRange;
141 Rm_osalFree((void *)rangeList, sizeof(Rm_ResourceRange));
142 rangeList = nextRange;
143 }
144 }
146 /* FUNCTION PURPOSE: Extracts values from a DTB
147 ***********************************************************************
148 * DESCRIPTION: Returns a list of values extracted from a DTB
149 * file. A value in the DTB is specified as <x> where
150 * x is a numerical value. Values can be chained in the
151 * DTB with comma separation.
152 * Example:
153 * <10>,
154 * <20>,
155 * <30>;
156 * Results in a list of three values.
157 */
158 static Rm_ResourceValue *dtbUtilCommonExtractValueList(const void *dtbDataPtr,
159 int32_t dtbDataLen)
160 {
161 uint32_t *dtbRangeData = (uint32_t *)dtbDataPtr;
162 Rm_ResourceValue *startValue = NULL;
163 Rm_ResourceValue *newValue = NULL;
164 Rm_ResourceValue *prevValue = NULL;
165 uint32_t i;
167 /* Values are stored in the DTB as a list of 32-bit words. The DTB
168 * gives properties lengths in bytes so the length returned from the DTB
169 * should be a multiple of the number of bytes a uint32_t. */
170 if (dtbDataLen % sizeof(uint32_t)) {
171 return (NULL);
172 }
174 for (i = 0; i < (dtbDataLen / sizeof(uint32_t)); i++) {
175 newValue = (Rm_ResourceValue *) Rm_osalMalloc(sizeof(Rm_ResourceValue));
176 newValue->value = fdt32_to_cpu(dtbRangeData[i]);
177 newValue->nextValue = NULL;
179 if (prevValue == NULL) {
180 startValue = newValue;
181 } else {
182 prevValue->nextValue = newValue;
183 }
184 prevValue = newValue;
185 }
186 return(startValue);
187 }
189 /* FUNCTION PURPOSE: Deletes a value list
190 ***********************************************************************
191 * DESCRIPTION: Frees the memory associated with a list of values
192 * that were extracted from a DTB.
193 */
194 static void dtbUtilCommonFreeValueList (Rm_ResourceValue *valueList)
195 {
196 Rm_ResourceValue *nextValue;
198 while (valueList) {
199 nextValue = valueList->nextValue;
200 Rm_osalFree((void *)valueList, sizeof(Rm_ResourceValue));
201 valueList = nextValue;
202 }
203 }
205 /**********************************************************************
206 ************** Global Resource List Parsing Functions ****************
207 **********************************************************************/
209 /* FUNCTION PURPOSE: Returns the GRL property type
210 ***********************************************************************
211 * DESCRIPTION: Returns the GRL property type associated with the
212 * property name specified.
213 */
214 Rm_ResourcePropType rmDtbUtilResGetPropertyType(const char * propertyName)
215 {
216 Rm_ResourcePropType propertyType;
218 if(strcmp(dtbUtilResRangeProp, propertyName) == 0) {
219 propertyType = Rm_resourcePropType_RESOURCE_RANGE;
220 } else if(strcmp(dtbUtilResLinuxAliasProp, propertyName) == 0) {
221 propertyType = Rm_resourcePropType_RESOURCE_LINUX_ALIAS;
222 } else if(strcmp(dtbUtilResNsAssignmentProp, propertyName) == 0) {
223 propertyType = Rm_resourcePropType_NSASSIGNMENT;
224 } else {
225 propertyType = Rm_resourcePropType_UNKNOWN;
226 }
227 return(propertyType);
228 }
230 /* FUNCTION PURPOSE: Extracts a resource range list from a GRL DTB
231 ***********************************************************************
232 * DESCRIPTION: Returns a list of resource ranges extracted from a GRL
233 * DTB. A resource range in the DTB is specified as <x y>
234 * where x is resource base and y is a resource length
235 * starting from x. Resource ranges can be chained in the
236 * GRL DTB with comma separation.
237 * Example:
238 * <0 10>,
239 * <10 10>,
240 * <20 10>;
241 * Results in a list of three resource ranges.
242 */
243 Rm_ResourceRange *rmDtbUtilResExtractRange(const void *dtbDataPtr,
244 int32_t dtbDataLen)
245 {
246 return(dtbUtilCommonExtractRange(dtbDataPtr, dtbDataLen));
247 }
249 /* FUNCTION PURPOSE: Deletes a resource range list
250 ***********************************************************************
251 * DESCRIPTION: Frees the memory associated with a list of resource
252 * ranges that were extracted from a GRL DTB.
253 */
254 void rmDtbUtilResFreeRange(Rm_ResourceRange *rangeList)
255 {
256 dtbUtilCommonFreeRangeList(rangeList);
257 }
259 /* FUNCTION PURPOSE: Extracts a Linux alias list from a GRL DTB
260 ***********************************************************************
261 * DESCRIPTION: Returns a list of Linux alias paths extracted from a GRL
262 * DTB. A Linux alias path in the DTB is specified as a
263 * space separated string following by list of numerical
264 * values. Each word within the space separated string
265 * defines a node from the Linux DTB in the path to the
266 * Linux alias value for the resource. The numerical values
267 * specify the number of values at the end of the path in
268 * the Linux DTB. Linux alias paths can be chained in the
269 * GRL DTB with comma separation.
270 * Example:
271 * "LinuxDtbNode1 LinuxDtbNode2 resourcehere", <1 1>,
272 * "LinuxDtbNode1 LinuxDtbNode2 anotherRes", <2 2 3>,
273 * Results in a list of two Linux alias paths.
274 */
275 Rm_LinuxAlias *rmDtbUtilResExtractLinuxAlias(const void *dtbDataPtr,
276 int32_t dtbDataLen,
277 int32_t *result)
278 {
279 uint8_t *dtbAliasData = (uint8_t *)dtbDataPtr;
280 uint32_t pathLenBytes;
281 uint32_t extractedValue;
282 uint8_t *extractedValueBytePtr;
283 Rm_LinuxAlias *startAlias = NULL;
284 Rm_LinuxAlias *newAlias = NULL;
285 Rm_LinuxAlias *prevAlias = NULL;
286 uint32_t numOffsets;
287 int32_t i = 0;
288 uint16_t j;
290 /* Linux aliases are stored in the DTB as a list space-separated path node
291 * names within null terminated string. Following the path string will be
292 * two or three values specifying the fields in the linux DTB property that
293 * contain the relevant data. The first value specifies the number of
294 * offsets that follow. If two field offsets are specified the Linux DTB
295 * contains a base + length. If one field offset is specified the Linux
296 * DTB contains a single value for reservation. There is no padding
297 * between the path string and the 32-bit offsets. Therefore the 32-bit
298 * offsets may not be on a 4-byte boundary and must be constructed upon
299 * extraction */
300 while(i < dtbDataLen) {
301 newAlias = (Rm_LinuxAlias *) Rm_osalMalloc(sizeof(Rm_LinuxAlias));
303 pathLenBytes = strlen((char *) &dtbAliasData[i]) + 1;
304 newAlias->path = (char *) Rm_osalMalloc(pathLenBytes);
305 rm_strncpy(newAlias->path, ((char *) &dtbAliasData[i]), pathLenBytes);
307 /* Extract 32-bit value specifying number of offsets that follow */
308 i += pathLenBytes;
309 extractedValueBytePtr = (uint8_t *)&extractedValue;
310 for (j = 0; j < sizeof(uint32_t); j++, i++) {
311 extractedValueBytePtr[j] = dtbAliasData[i];
312 }
313 numOffsets = fdt32_to_cpu(extractedValue);
315 if ((numOffsets == 1) || (numOffsets == 2)) {
316 /* Always extract the base value */
317 extractedValueBytePtr = (uint8_t *)&extractedValue;
318 for (j = 0; j < sizeof(uint32_t); j++, i++) {
319 extractedValueBytePtr[j] = dtbAliasData[i];
320 }
321 newAlias->baseOffset = fdt32_to_cpu(extractedValue);
323 if (numOffsets == 2) {
324 for (j = 0; j < sizeof(uint32_t); j++, i++) {
325 extractedValueBytePtr[j] = dtbAliasData[i];
326 }
327 newAlias->lengthOffset = fdt32_to_cpu(extractedValue);
328 } else {
329 newAlias->lengthOffset = RM_DTB_UTIL_LINUX_ALIAS_OFFSET_NOT_SET;
330 }
332 newAlias->nextLinuxAlias = NULL;
333 if (prevAlias == NULL) {
334 startAlias = newAlias;
335 } else {
336 prevAlias->nextLinuxAlias = newAlias;
337 }
338 prevAlias = newAlias;
339 } else {
340 Rm_osalFree((void *)newAlias->path, pathLenBytes);
341 Rm_osalFree((void *)newAlias, sizeof(Rm_LinuxAlias));
342 while (startAlias) {
343 newAlias = startAlias->nextLinuxAlias;
344 pathLenBytes = strlen(startAlias->path);
345 Rm_osalFree((void *)startAlias->path, pathLenBytes + 1);
346 Rm_osalFree((void *)startAlias, sizeof(Rm_LinuxAlias));
347 startAlias = newAlias;
348 }
349 *result = RM_ERROR_GRL_INVALID_LINUX_ALIAS_FORMAT;
350 return(NULL);
351 }
352 }
353 return(startAlias);
354 }
356 /* FUNCTION PURPOSE: Deletes a Linux Alias list
357 ***********************************************************************
358 * DESCRIPTION: Frees the memory associated with a list of Linux
359 * aliases that were extracted from a GRL DTB.
360 */
361 void rmDtbUtilResFreeLinuxAlias(Rm_LinuxAlias *aliasList)
362 {
363 Rm_LinuxAlias *nextAlias;
364 int32_t pathSize;
366 while (aliasList) {
367 nextAlias = aliasList->nextLinuxAlias;
368 pathSize = strlen(aliasList->path);
369 Rm_osalFree((void *)aliasList->path, pathSize + 1);
370 Rm_osalFree((void *)aliasList, sizeof(Rm_LinuxAlias));
371 aliasList = nextAlias;
372 }
373 }
375 /* FUNCTION PURPOSE: Extracts a NS assignment list from a GRL DTB
376 ***********************************************************************
377 * DESCRIPTION: Returns a list of NameServer assignments extracted from
378 * a GRL DTB. A NameServer assignment is specified with
379 * a string representing the NameServer name following by
380 * a range in <base length> format. NameServer assignments
381 * can be chained in the GRL DTB with comma separation.
382 * Example:
383 * "Name1", <0 10>,
384 * "Name2", <10 10>,
385 * "Another Name", <20 10>;
386 * Results in a list of three NameServer assignments.
387 */
388 Rm_NsAssignment *rmDtbUtilResExtractNsAssignment(const void *dtbDataPtr,
389 int32_t dtbDataLen,
390 int32_t *result)
391 {
392 uint8_t *dtbNsAssignmentData = (uint8_t *)dtbDataPtr;
393 uint32_t nameLenBytes;
394 uint32_t extractedValue;
395 uint8_t *extractedValueBytePtr;
396 Rm_NsAssignment *startAssignment = NULL;
397 Rm_NsAssignment *newAssignment = NULL;
398 Rm_NsAssignment *prevAssignment = NULL;
399 int32_t i = 0;
400 uint16_t j;
402 /* NameServer assignments are stored in the DTB as a null-terminated
403 * character string followed by a 32-bit word containing the value to be
404 * assigned to the name in the string. There is no padding between the
405 * string and the 32-bit word. Therefore the 32-bit word may not be on a
406 * 4-byte boundary and must be constructed upon extraction */
407 while(i < dtbDataLen) {
408 newAssignment = (Rm_NsAssignment *)Rm_osalMalloc(sizeof(Rm_NsAssignment));
410 nameLenBytes = strlen((char *) &dtbNsAssignmentData[i]) + 1;
411 if (nameLenBytes > RM_NAME_MAX_CHARS) {
412 Rm_osalFree((void *)newAssignment, sizeof(Rm_NsAssignment));
413 while (startAssignment) {
414 newAssignment = startAssignment->nextNsAssignment;
415 Rm_osalFree((void *)startAssignment, sizeof(Rm_NsAssignment));
416 startAssignment = newAssignment;
417 }
418 *result = RM_ERROR_NAMESERVER_NAME_TOO_LONG;
419 return(NULL);
420 }
421 rm_strncpy(newAssignment->nsName, ((char *) &dtbNsAssignmentData[i]),
422 RM_NAME_MAX_CHARS);
424 /* Extract 32-bit base value and flip endian */
425 i += nameLenBytes;
426 extractedValueBytePtr = (uint8_t *)&extractedValue;
427 for (j = 0; j < sizeof(uint32_t); j++, i++) {
428 extractedValueBytePtr[j] = dtbNsAssignmentData[i];
429 }
430 newAssignment->resourceBase = fdt32_to_cpu(extractedValue);
432 /* Extract 32-bit length value and flip endian */
433 for (j = 0; j < sizeof(uint32_t); j++, i++) {
434 extractedValueBytePtr[j] = dtbNsAssignmentData[i];
435 }
436 newAssignment->resourceLength = fdt32_to_cpu(extractedValue);
438 newAssignment->nextNsAssignment = NULL;
439 if (prevAssignment == NULL) {
440 startAssignment = newAssignment;
441 } else {
442 prevAssignment->nextNsAssignment = newAssignment;
443 }
444 prevAssignment = newAssignment;
445 }
447 return(startAssignment);
448 }
450 /* FUNCTION PURPOSE: Deletes a NameServer assignment list
451 ***********************************************************************
452 * DESCRIPTION: Frees the memory associated with a list of NameServer
453 * assignments that were extracted from a GRL DTB.
454 */
455 void rmDtbUtilResFreeNsAssignmentList (Rm_NsAssignment *nsAssignmentList)
456 {
457 Rm_NsAssignment *nextAssignment;
459 while (nsAssignmentList) {
460 nextAssignment = nsAssignmentList->nextNsAssignment;
461 Rm_osalFree((void *)nsAssignmentList, sizeof(Rm_NsAssignment));
462 nsAssignmentList = nextAssignment;
463 }
464 }
466 /**********************************************************************
467 ********************** Policy Parsing Functions **********************
468 **********************************************************************/
470 /* FUNCTION PURPOSE: Returns the Policy property type
471 ***********************************************************************
472 * DESCRIPTION: Returns the Policy property type associated with the
473 * property name specified.
474 */
475 Rm_PolicyPropType rmDtbUtilPolicyGetPropertyType(const char * propertyName)
476 {
477 Rm_PolicyPropType propertyType;
479 if(strcmp(dtbUtilPolicyAssignments, propertyName) == 0) {
480 propertyType = Rm_policyPropType_ASSIGNMENTS;
481 } else if(strcmp(dtbUtilPolicyCdAllocationSize, propertyName) == 0) {
482 propertyType = Rm_policyPropType_CD_ALLOCATION_SIZE;
483 } else if(strcmp(dtbUtilPolicyAllocationAlignment, propertyName) == 0) {
484 propertyType = Rm_policyPropType_ALLOCATION_ALIGNMENT;
485 } else if(strcmp(dtbUtilPolicyValidInstances, propertyName) == 0) {
486 propertyType = Rm_policyPropType_VALID_INSTANCES;
487 } else {
488 propertyType = Rm_policyPropType_UNKNOWN;
489 }
490 return(propertyType);
491 }
493 /* FUNCTION PURPOSE: Extracts a policy assignment list from a Policy DTB
494 ***********************************************************************
495 * DESCRIPTION: Returns a list of policy assignments extracted from a
496 * Policy DTB. A policy assignment in the DTB is
497 * specified as <x y>, "permissions string" where x is
498 * resource base and y is a resource length starting
499 * from x. "permissions string" is string specifying
500 * which RM instances are allowed to use the resource
501 * range. Policy assignments can be chained in the
502 * Policy DTB with comma separation.
503 * Example:
504 * <0 10>, "iux = (Rm_Client)",
505 * <10 10>, "iu = (*);
506 * Results in a list of two policy assignments.
507 */
508 Rm_PolicyAssignment *rmDtbUtilPolicyExtractAssignments(const void *dtbDataPtr,
509 int32_t dtbDataLen)
510 {
511 uint8_t *dtbAssignmentData = (uint8_t *)dtbDataPtr;
512 uint32_t permissionsLenBytes;
513 uint32_t extractedValue;
514 uint8_t *extractedValueBytePtr;
515 Rm_PolicyAssignment *startAssignment = NULL;
516 Rm_PolicyAssignment *newAssignment = NULL;
517 Rm_PolicyAssignment *prevAssignment = NULL;
518 int32_t i = 0;
519 uint16_t j;
521 /* Policy assignments are stored in the DTB as two 32-bit words containing
522 * a resource base and length to be assigned the permissions in the defined
523 * in the string that follows. There is no padding between the 32-bit
524 * words and the string. Therefore the 32-bit word may not be on a 4-byte
525 * boundary and must be constructed upon extraction */
526 while(i < dtbDataLen) {
527 newAssignment = (Rm_PolicyAssignment *)Rm_osalMalloc(sizeof(Rm_PolicyAssignment));
529 /* Extract 32-bit resource base value and flip endianness */
530 extractedValueBytePtr = (uint8_t *)&extractedValue;
531 for (j = 0; j < sizeof(uint32_t); j++, i++) {
532 extractedValueBytePtr[j] = dtbAssignmentData[i];
533 }
534 newAssignment->resourceBase = fdt32_to_cpu(extractedValue);
536 /* Extract 32-bit resource length value and flip endianness */
537 for (j = 0; j < sizeof(uint32_t); j++, i++) {
538 extractedValueBytePtr[j] = dtbAssignmentData[i];
539 }
540 newAssignment->resourceLength = fdt32_to_cpu(extractedValue);
542 permissionsLenBytes = strlen((char *) &dtbAssignmentData[i]) + 1;
543 newAssignment->permissionsList = (char *)Rm_osalMalloc(permissionsLenBytes);
544 rm_strncpy(newAssignment->permissionsList,
545 ((char *)&dtbAssignmentData[i]), permissionsLenBytes);
546 i += permissionsLenBytes;
548 newAssignment->nextAssignment = NULL;
549 if (prevAssignment == NULL) {
550 startAssignment = newAssignment;
551 } else {
552 prevAssignment->nextAssignment = newAssignment;
553 }
554 prevAssignment = newAssignment;
555 }
556 return(startAssignment);
557 }
559 /* FUNCTION PURPOSE: Deletes a policy assignment list
560 ***********************************************************************
561 * DESCRIPTION: Frees the memory associated with a list of policy
562 * assignments that were extracted from a Policy DTB.
563 */
564 void rmDtbUtilPolicyFreeAssignments(Rm_PolicyAssignment *assignmentList)
565 {
566 Rm_PolicyAssignment *nextAssignment;
567 int32_t permissionsSize;
569 while (assignmentList) {
570 nextAssignment = assignmentList->nextAssignment;
571 permissionsSize = strlen(assignmentList->permissionsList);
572 Rm_osalFree((void *)assignmentList->permissionsList, permissionsSize+1);
573 Rm_osalFree((void *)assignmentList, sizeof(Rm_PolicyAssignment));
574 assignmentList = nextAssignment;
575 }
576 }
578 /* FUNCTION PURPOSE: Extracts a CD allocation size from a Policy DTB
579 ***********************************************************************
580 * DESCRIPTION: Returns a list of allocation sizes extracted from a
581 * Policy DTB. A allocation size in the DTB is specified
582 * as <x> where x is the allocation size for a resource.
583 * Allocation sizes can be chained in the Policy DTB with
584 * comma separation.
585 * Example:
586 * <10>,
587 * <100>;
588 * Results in a list of two allocation sizes.
589 */
590 Rm_ResourceValue *rmDtbUtilPolicyExtractCdAllocationSizes(const void *dtbDataPtr,
591 int32_t dtbDataLen)
592 {
593 return(dtbUtilCommonExtractValueList(dtbDataPtr, dtbDataLen));
594 }
596 /* FUNCTION PURPOSE: Deletes a CD allocation sizes list
597 ***********************************************************************
598 * DESCRIPTION: Frees the memory associated with a list of allocation
599 * sizes that were extracted from a Policy DTB.
600 */
601 void rmDtbUtilPolicyFreeCdAllocationSizes (Rm_ResourceValue *allocationSizeList)
602 {
603 dtbUtilCommonFreeValueList(allocationSizeList);
604 }
606 /* FUNCTION PURPOSE: Extracts an resource alignment from a Policy DTB
607 ***********************************************************************
608 * DESCRIPTION: Returns a list of resource alignments extracted from a
609 * Policy DTB. A resource alignment in the DTB is specified
610 * as <x> where x is the resource alignment for a resource.
611 * Resource alignments can be chained in the Policy DTB with
612 * comma separation.
613 * Example:
614 * <10>,
615 * <100>;
616 * Results in a list of two resource alignments.
617 */
618 Rm_ResourceValue *rmDtbUtilPolicyExtractResourceAlignments(const void *dtbDataPtr,
619 int32_t dtbDataLen)
620 {
621 return(dtbUtilCommonExtractValueList(dtbDataPtr, dtbDataLen));
622 }
624 /* FUNCTION PURPOSE: Deletes a resource alignments list
625 ***********************************************************************
626 * DESCRIPTION: Frees the memory associated with a list of resource
627 * alignments that were extracted from a Policy DTB.
628 */
629 void rmDtbUtilPolicyFreeResourceAlignments(Rm_ResourceValue *alignmentList)
630 {
631 dtbUtilCommonFreeValueList(alignmentList);
632 }
634 /* FUNCTION PURPOSE: Extracts an valid instance list from a Policy DTB
635 ***********************************************************************
636 * DESCRIPTION: Returns a list of valid instances extracted from a
637 * Policy DTB. A valid instance in the DTB is specified
638 * as "instName" where instName is the name of an RM
639 * instance. Valid instances can be chained in the
640 * Policy DTB with comma separation.
641 * Example:
642 * <Rm_Client>,
643 * <Rm_Server>;
644 * Results in a list of two valid instances.
645 */
646 Rm_PolicyValidInst *rmDtbUtilPolicyExtractValidInstances(const void *dtbDataPtr,
647 int32_t dtbDataLen,
648 int32_t *result)
649 {
650 uint8_t *dtbValidInstData = (uint8_t *)dtbDataPtr;
651 uint32_t instLenBytes;
652 Rm_PolicyValidInst *startInst = NULL;
653 Rm_PolicyValidInst *newInst = NULL;
654 Rm_PolicyValidInst *prevInst = NULL;
655 int32_t i = 0;
657 /* Valid RM instances are stored in the DTB as a list of null-terminated
658 * character strings. */
659 while(i < dtbDataLen) {
660 newInst = (Rm_PolicyValidInst *)Rm_osalMalloc(sizeof(Rm_PolicyValidInst));
662 instLenBytes = strlen((char *) &dtbValidInstData[i]) + 1;
663 if (instLenBytes > RM_NAME_MAX_CHARS) {
664 Rm_osalFree((void *)newInst, sizeof(Rm_PolicyValidInst));
665 while (startInst) {
666 newInst = startInst->nextValidInst;
667 Rm_osalFree((void *)startInst, sizeof(Rm_PolicyValidInst));
668 startInst = newInst;
669 }
670 *result = RM_ERROR_VALID_INST_NAME_TOO_LONG;
671 return(NULL);
672 }
673 rm_strncpy(newInst->instName, ((char *) &dtbValidInstData[i]),
674 instLenBytes);
676 i += instLenBytes;
678 newInst->nextValidInst = NULL;
680 if (prevInst == NULL) {
681 startInst = newInst;
682 } else {
683 prevInst->nextValidInst = newInst;
684 }
685 prevInst = newInst;
686 }
687 return(startInst);
688 }
690 /* FUNCTION PURPOSE: Deletes a valid instnace list
691 ***********************************************************************
692 * DESCRIPTION: Frees the memory associated with a list of valid
693 * instances that were extracted from a Policy DTB.
694 */
695 void rmDtbUtilPolicyFreeValidInstances (Rm_PolicyValidInst *validInstList)
696 {
697 Rm_PolicyValidInst *nextInst;
699 while (validInstList) {
700 nextInst = validInstList->nextValidInst;
701 Rm_osalFree((void *)validInstList, sizeof(Rm_PolicyValidInst));
702 validInstList = nextInst;
703 }
704 }
706 /**********************************************************************
707 ****************Linux DTB Parsing Defines and Functions***************
708 **********************************************************************/
710 /* FUNCTION PURPOSE: Extracts a linux value list from a Linux DTB
711 ***********************************************************************
712 * DESCRIPTION: Returns a list of values extracted from a Linux
713 * DTB. Linux value in the Linux DTB is specified
714 * as <w x y z ...> where w x y z ... are a list of
715 * numerical values.
716 * Example:
717 * <1 5 10 15 20 25>;
718 * Results in a list of six Linux values.
719 */
720 Rm_LinuxValueRange *rmDtbUtilLinuxExtractValues(const void *dtbDataPtr,
721 int32_t dtbDataLen)
722 {
723 uint32_t *dtbValueData = (uint32_t *)dtbDataPtr;
724 Rm_LinuxValueRange *startValue = NULL;
725 Rm_LinuxValueRange *newValue = NULL;
726 Rm_LinuxValueRange *prevValue = NULL;
727 uint32_t i;
729 /* Values are stored in the Linux DTB as a list of 32-bit words. The
730 * number of 32-bit words in the value field can differ. depending on the
731 * number of values specified. */
732 for (i = 0; i < (dtbDataLen / sizeof(uint32_t)); i++) {
733 newValue = (Rm_LinuxValueRange *)Rm_osalMalloc(sizeof(Rm_LinuxValueRange));
734 /* Endianness of extracted value must be flipped */
735 newValue->value = fdt32_to_cpu(dtbValueData[i]);
736 newValue->nextValue = NULL;
738 if (prevValue == NULL) {
739 startValue = newValue;
740 } else {
741 prevValue->nextValue = newValue;
742 }
743 prevValue = newValue;
744 }
745 return(startValue);
746 }
748 /* FUNCTION PURPOSE: Deletes a Linux values list
749 ***********************************************************************
750 * DESCRIPTION: Frees the memory associated with a list of Linux
751 * values that were extracted from a Linux DTB.
752 */
753 void rmDtbUtilLinuxFreeValues(Rm_LinuxValueRange *valueList)
754 {
755 Rm_LinuxValueRange *nextValue;
757 while (valueList) {
758 nextValue = valueList->nextValue;
759 Rm_osalFree((void *)valueList, sizeof(Rm_LinuxValueRange));
760 valueList = nextValue;
761 }
762 }