blob: 0c6aa999e0e7c331a996b83e7eaf08a509939426 [file] [log] [blame]
Julian Hallcfe2f5b2022-09-22 11:26:35 +01001/*
2 * Copyright (c) 2022, Arm Limited. All rights reserved.
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7
8#include <stddef.h>
9#include <stdint.h>
10#include <string.h>
Julian Hallcfe2f5b2022-09-22 11:26:35 +010011#include "volume_index.h"
12
13#ifndef VOLUME_INDEX_MAX_ENTRIES
Julian Hall4a658ac2022-10-20 10:44:49 +010014#define VOLUME_INDEX_MAX_ENTRIES (8)
Julian Hallcfe2f5b2022-09-22 11:26:35 +010015#endif
16
17/**
18 * Singleton index of volume IDs to IO devices.
19 */
Julian Hall4a658ac2022-10-20 10:44:49 +010020static struct {
21
Julian Hallcfe2f5b2022-09-22 11:26:35 +010022 size_t size;
Julian Hall4a658ac2022-10-20 10:44:49 +010023 struct {
Julian Hallcfe2f5b2022-09-22 11:26:35 +010024 unsigned int volume_id;
Julian Hall4a658ac2022-10-20 10:44:49 +010025 struct volume *volume;
Julian Hallcfe2f5b2022-09-22 11:26:35 +010026 } entries[VOLUME_INDEX_MAX_ENTRIES];
27
28} volume_index;
29
30/**
31 * @brief Gets a device for volume IO operations
32 *
33 * @param[in] volume_id Identifies the image
34 * @param[out] dev_handle Handle for IO operations
Julian Hall4a658ac2022-10-20 10:44:49 +010035 * @param[out] io_spec Opaque configuration data
Julian Hallcfe2f5b2022-09-22 11:26:35 +010036 *
37 * This function realizes the interface expected by tf-a components to
38 * provide a concrete IO device for the specified volume ID. When used in
39 * TS deployments, the set of IO devices required for a deployment
40 * are registered during service configuration.
41 */
42int plat_get_image_source(
43 unsigned int volume_id,
44 uintptr_t *dev_handle,
Julian Hall4a658ac2022-10-20 10:44:49 +010045 uintptr_t *io_spec)
Julian Hallcfe2f5b2022-09-22 11:26:35 +010046{
Julian Hall4a658ac2022-10-20 10:44:49 +010047 struct volume *volume = NULL;
48 int result = volume_index_find(volume_id, &volume);
Julian Hallcfe2f5b2022-09-22 11:26:35 +010049
Julian Hall4a658ac2022-10-20 10:44:49 +010050 if (result == 0) {
Julian Hallcfe2f5b2022-09-22 11:26:35 +010051
Julian Hall4a658ac2022-10-20 10:44:49 +010052 if (volume) {
Julian Hallcfe2f5b2022-09-22 11:26:35 +010053
Julian Hall4a658ac2022-10-20 10:44:49 +010054 *dev_handle = volume->dev_handle;
55 *io_spec = volume->io_spec;
56 } else
57 result = -1;
Julian Hallcfe2f5b2022-09-22 11:26:35 +010058 }
59
60 return result;
61}
62
63void volume_index_init(void)
64{
65 volume_index_clear();
66}
67
68void volume_index_clear(void)
69{
70 memset(&volume_index, 0, sizeof(volume_index));
71}
72
73int volume_index_add(
74 unsigned int volume_id,
Julian Hall4a658ac2022-10-20 10:44:49 +010075 struct volume *volume)
Julian Hallcfe2f5b2022-09-22 11:26:35 +010076{
77 int result = -1;
78
Julian Hall4a658ac2022-10-20 10:44:49 +010079 if (volume_index.size < VOLUME_INDEX_MAX_ENTRIES) {
Julian Hallcfe2f5b2022-09-22 11:26:35 +010080 size_t i = volume_index.size;
81
82 ++volume_index.size;
83 volume_index.entries[i].volume_id = volume_id;
Julian Hall4a658ac2022-10-20 10:44:49 +010084 volume_index.entries[i].volume = volume;
Julian Hallcfe2f5b2022-09-22 11:26:35 +010085
86 result = 0;
87 }
88
89 return result;
90}
Julian Hall4a658ac2022-10-20 10:44:49 +010091
92int volume_index_find(
93 unsigned int volume_id,
94 struct volume **volume)
95{
96 int result = -1;
97
98 for (size_t i = 0; i < volume_index.size; i++) {
99
100 if (volume_index.entries[i].volume_id == volume_id) {
101
102 *volume = volume_index.entries[i].volume;
103 result = 0;
104 break;
105 }
106 }
107
108 return result;
109}
110
111struct volume *volume_index_get(unsigned int index)
112{
113 struct volume *volume = NULL;
114
115 if (index < volume_index.size)
116 volume = volume_index.entries[index].volume;
117
118 return volume;
119}