blob: db42a3e68fffc92a0dece94362e3b87a7501011f [file] [log] [blame]
The Android Open Source Projectdd7bc332009-03-03 19:32:55 -08001
2/*
3 * Copyright (C) 2008 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 * http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17
18#include <stdlib.h>
19#include <string.h>
20#include <dirent.h>
21#include <errno.h>
22
23#include <sys/types.h>
24
25#include "vold.h"
26#include "media.h"
27
28static media_list_t *list_root = NULL;
29
30media_t *media_create(char *devpath, char *name, char *serial, media_type_t type)
31{
32 media_list_t *list_entry;
33 media_t *new;
34
35 if (!(new = malloc(sizeof(media_t))))
36 return NULL;
37
38 memset(new, 0, sizeof(media_t));
39
40 if (!(list_entry = malloc(sizeof(media_list_t)))) {
41 free(new);
42 return NULL;
43 }
44 list_entry->media = new;
45 list_entry->next = NULL;
46
47 if (!list_root)
48 list_root = list_entry;
49 else {
50 media_list_t *list_scan = list_root;
51 while(list_scan->next)
52 list_scan = list_scan->next;
53 list_scan->next = list_entry;
54 }
55
56 new->devpath = strdup(devpath);
57 new->name = strdup(name);
58 if (!serial)
59 new->serial = 0;
60 else
61 new->serial = strtoul(serial, NULL, 0);
62
63 new->media_type = type;
64
65 return new;
66}
67
68void media_destroy(media_t *media)
69{
70 media_list_t *list_next;
71
72 if (list_root->media == media) {
73 list_next = list_root->next;
74 free(list_root);
75 list_root = list_next;
76 } else {
77 media_list_t *list_scan = list_root;
78 while (list_scan->next->media != media)
79 list_scan = list_scan -> next;
80 list_next = list_scan->next->next;
81 free(list_scan->next);
82 list_scan->next = list_next;
83 }
84
85 free(media->devpath);
86 free(media->name);
87
88 while(media->devs)
89 media_remove_blkdev(media, media->devs->dev);
90 free(media);
91}
92
93media_t *media_lookup_by_path(char *devpath, boolean fuzzy_match)
94{
95 media_list_t *list_scan = list_root;
96
97 while (list_scan) {
98 if (fuzzy_match) {
99 if (!strncmp(list_scan->media->devpath, devpath, strlen(devpath)))
100 return list_scan->media;
101 } else {
102 if (!strcmp(list_scan->media->devpath, devpath))
103 return list_scan->media;
104 }
105 list_scan = list_scan->next;
106 }
107#if DEBUG_MEDIA
108 LOG_VOL("media_lookup_by_path(): No media found @ %s", devpath);
109#endif
110 return NULL;
111}
112
113int media_add_blkdev(media_t *card, blkdev_t *dev)
114{
115 blkdev_list_t *list_entry;
116
The Android Open Source Projecte037fd72009-03-13 13:04:37 -0700117 if (!(list_entry = malloc(sizeof(blkdev_list_t))))
The Android Open Source Projectdd7bc332009-03-03 19:32:55 -0800118 return -ENOMEM;
The Android Open Source Projectdd7bc332009-03-03 19:32:55 -0800119
120 list_entry->next = NULL;
121 list_entry->dev = dev;
122 if (!card->devs)
123 card->devs = list_entry;
124 else {
125 blkdev_list_t *scan = card->devs;
126
127 while(scan->next)
128 scan = scan->next;
129
130 scan->next = list_entry;
131 }
132 return 0;
133}
134
135void media_remove_blkdev(media_t *card, blkdev_t *dev)
136{
137 if (card->devs->dev == dev)
138 card->devs = card->devs->next;
139 else {
140 blkdev_list_t *scan = card->devs;
141 while (scan->next->dev != dev)
142 scan = scan -> next;
143 blkdev_list_t *next = scan->next->next;
144 free(scan->next);
145 scan->next = next;
146 }
147}
148
149media_t *media_lookup_by_dev(blkdev_t *dev)
150{
151 media_list_t *media_scan = list_root;
152
153 while (media_scan) {
154 blkdev_list_t *blk_scan = media_scan->media->devs;
155 while (blk_scan) {
156 if (blk_scan->dev == dev)
157 return media_scan->media;
158 blk_scan = blk_scan->next;
159 }
160 media_scan = media_scan->next;
161 }
162 return NULL;
163}