]> git.saurik.com Git - apple/bootx.git/blob - bootx.tproj/fs.subproj/fs.c
8f8f02a4f9c03c4a09dcdf5f7569a6a5c837f162
[apple/bootx.git] / bootx.tproj / fs.subproj / fs.c
1 /*
2 * Copyright (c) 2000 Apple Computer, Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * The contents of this file constitute Original Code as defined in and
7 * are subject to the Apple Public Source License Version 1.1 (the
8 * "License"). You may not use this file except in compliance with the
9 * License. Please obtain a copy of the License at
10 * http://www.apple.com/publicsource and read it before using this file.
11 *
12 * This Original Code and all software distributed under the License are
13 * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
14 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
15 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the
17 * License for the specific language governing rights and limitations
18 * under the License.
19 *
20 * @APPLE_LICENSE_HEADER_END@
21 */
22 /*
23 * fs.c - Generic access to the file system modules.
24 *
25 * Copyright (c) 1999-2000 Apple Computer, Inc.
26 *
27 * DRI: Josh de Cesare
28 */
29
30 #include <sl.h>
31
32 typedef long (* FSLoadFile)(CICell ih, char *filePath);
33 typedef long (* FSGetDirEntry)(CICell ih, char *dirPath,
34 long *dirIndex, char **name,
35 long *flags, long *time);
36
37 #define kPartNet (0)
38 #define kPartHFS (1)
39 #define kPartUFS (2)
40 #define kPartExt2 (3)
41
42 struct PartInfo {
43 long partType;
44 CICell partIH;
45 FSLoadFile loadFile;
46 FSGetDirEntry getDirEntry;
47 char partName[1024];
48 };
49 typedef struct PartInfo PartInfo, *PartInfoPtr;
50
51 #define kNumPartInfos (16)
52 static PartInfo gParts[kNumPartInfos];
53
54 // Private function prototypes
55 long LookupPartition(char *devSpec);
56
57
58 // Public functions
59
60 long LoadFile(char *fileSpec)
61 {
62 char devSpec[256];
63 char *filePath;
64 FSLoadFile loadFile;
65 long ret, length, partIndex;
66
67 ret = ConvertFileSpec(fileSpec, devSpec, &filePath);
68 if ((ret == -1) || (filePath == NULL)) return -1;
69
70 // Get the partition index for devSpec.
71 partIndex = LookupPartition(devSpec);
72 if (partIndex == -1) return -1;
73
74 loadFile = gParts[partIndex].loadFile;
75 length = loadFile(gParts[partIndex].partIH, filePath);
76
77 // if (length == 0) return -1;
78
79 return length;
80 }
81
82 long GetFileInfo(char *dirSpec, char *name, long *flags, long *time)
83 {
84 long ret, index = 0;
85 char *curName;
86
87 while (1) {
88 ret = GetDirEntry(dirSpec, &index, &curName, flags, time);
89 if (ret == -1) break;
90
91 if (!strcmp(name, curName)) break;
92 }
93
94 return ret;
95 }
96
97 long GetDirEntry(char *dirSpec, long *dirIndex, char **name,
98 long *flags, long *time)
99 {
100 char devSpec[256];
101 char *dirPath;
102 FSGetDirEntry getDirEntry;
103 long ret, partIndex;
104
105 ret = ConvertFileSpec(dirSpec, devSpec, &dirPath);
106 if ((ret == -1) || (dirPath == NULL)) return -1;
107
108 // Get the partition index for devSpec.
109 partIndex = LookupPartition(devSpec);
110 if (partIndex == -1) return -1;
111
112 getDirEntry = gParts[partIndex].getDirEntry;
113 ret = getDirEntry(gParts[partIndex].partIH, dirPath,
114 dirIndex, name, flags, time);
115
116 return ret;
117 }
118
119 long DumpDir(char *dirSpec)
120 {
121 long ret, flags, time, index = 0;
122 char *name;
123
124 printf("DumpDir on [%s]\n", dirSpec);
125
126 while (1) {
127 ret = GetDirEntry(dirSpec, &index, &name, &flags, &time);
128 if (ret == -1) break;
129
130 printf("%x %x [%s]\n", flags, time, name);
131 }
132
133 return 0;
134 }
135
136
137 // Private functions
138
139 long LookupPartition(char *devSpec)
140 {
141 CICell partIH;
142 long partIndex, partType;
143 long deviceType;
144
145 // See if the devSpec has already been opened.
146 for (partIndex = 0; partIndex < kNumPartInfos; partIndex++) {
147 if (!strcmp(gParts[partIndex].partName, devSpec)) break;
148 }
149
150 // If it has not been opened, do so now.
151 if (partIndex == kNumPartInfos) {
152 // Find a free slot.
153 for (partIndex = 0; partIndex < kNumPartInfos; partIndex++) {
154 if (gParts[partIndex].partIH == 0) break;
155 }
156 // No free slots, so return error.
157 if (partIndex == kNumPartInfos) return -1;
158
159 deviceType = GetDeviceType(devSpec);
160 switch (deviceType) {
161 case kNetworkDeviceType :
162 partIH = NetInitPartition(devSpec);
163 if (partIH == 0) return -1;
164 partType = kPartNet;
165 break;
166
167 case kBlockDeviceType :
168 printf("Opening partition [%s]...\n", devSpec);
169 partIH = Open(devSpec);
170 if (partIH == 0) {
171 printf("Failed to open partition [%s].\n", devSpec);
172 return -1;
173 }
174
175 // Find out what kind of partition it is.
176 if (HFSInitPartition(partIH) != -1) partType = kPartHFS;
177 else if (UFSInitPartition(partIH) != -1) partType = kPartUFS;
178 else if (Ext2InitPartition(partIH) != -1) partType = kPartExt2;
179 else return -1;
180 break;
181
182 default :
183 return -1;
184 }
185
186 gParts[partIndex].partIH = partIH;
187 gParts[partIndex].partType = partType;
188 strcpy(gParts[partIndex].partName, devSpec);
189
190 switch (partType) {
191 case kPartNet:
192 gParts[partIndex].loadFile = NetLoadFile;
193 gParts[partIndex].getDirEntry = NetGetDirEntry;
194 break;
195
196 case kPartHFS:
197 gParts[partIndex].loadFile = HFSLoadFile;
198 gParts[partIndex].getDirEntry = HFSGetDirEntry;
199 break;
200
201 case kPartUFS:
202 gParts[partIndex].loadFile = UFSLoadFile;
203 gParts[partIndex].getDirEntry = UFSGetDirEntry;
204 break;
205
206 case kPartExt2:
207 gParts[partIndex].loadFile = Ext2LoadFile;
208 gParts[partIndex].getDirEntry = Ext2GetDirEntry;
209 break;
210 }
211 }
212
213 return partIndex;
214 }