summaryrefslogtreecommitdiff
path: root/v4.0/src/CMD/FDISK/DISKOUT.C
blob: 189795e17e0fc18e7c64d4ac5d662e20e650420c (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
#include "dos.h"                                                        /* AN000 */
#include "fdisk.h"                                                      /* AN000 */
#include "subtype.h"                                                    /* AN000 */
#include "extern.h"                                                     /* AN000 */


/*  */
void write_info_to_disk()

BEGIN

char            i;
unsigned char   j;
unsigned        extended_location;
char            extended_index;
char            temp;
char            first_found;
char            changed_flag;
char            temp_disk;


        temp = c(NUL);                                                  /* AN009 */
        temp_disk = cur_disk;
        /* See if need to update the master boot record */
        for (j = uc(0); j < number_of_drives; j++)                      /* AC000 */
           BEGIN

            /* Save disk number */
            cur_disk = ((char)(j));

            /* See if there were any errors on that drive */
            if (good_disk[j])
               BEGIN
                for (i=c(0); i < c(4); i++)                             /* AC000 */
                   BEGIN
                    if (part_table[j][i].changed)
                       BEGIN
                        write_master_boot_to_disk(j);
                        break;
                       END
                   END
                /* See if the extended partition exists - if not, don't fool with the logical*/
                /* drives - there is nothing to point to thier structures. Otherwise you get into */
                /* a chicken and the egg situation, where you are trying to write out 'deletes' of */
                /* the logical drive based on the start of the extended partition, but there isn't one */
                /* because it has already been deleted already. Bad things happen - PTM P941  */

                if (find_partition_type(uc(EXTENDED)));                 /* AC000 */
                   BEGIN
                    /* See if any extended partitions need to be updated */
                    changed_flag = FALSE;

                    for (i=c(0);i <c(23); i++)                          /* AC000 */
                       BEGIN
                        if (ext_table[j][i].changed)
                           BEGIN
                            changed_flag = TRUE;
                            break;
                           END
                       END
                    if (changed_flag)
                       BEGIN
                        /* First,get them in order - drive letters are assigned in the order */
                        /* that they exist on the disk */
                        sort_ext_table(c(23));                          /* AC000 */

                        for (i=c(0);i < c(23); i++)                     /* AC000 */

                           BEGIN
                            /* If there is a valid drive existing, write it out */
                            if (ext_table[j][sort[i]].sys_id != uc(0))  /* AC000 */
                               BEGIN
                                write_ext_boot_to_disk(i,j);
                               END
                           END

                        /* Find start of extended partition */
                        extended_index = find_partition_location(uc(EXTENDED));     /* AC000 */
                        extended_location = part_table[j][extended_index].start_cyl;

                        /* See if the first entry in EXTENDED DOS partition will be written out */
                        /* Need to find the first drive in the sorted list */
                        for (i=c(0);i < c(23); i++)                     /* AC000 */
                           BEGIN
                            if (ext_table[j][sort[i]].sys_id != uc(0))  /* AC000 */
                               BEGIN
                                temp = sort[i];
                                break;
                               END
                           END
                        /* See if drive written out */
                        if ((temp != c(NUL)) &&
                            (extended_location != ext_table[j][temp].start_cyl))   /* AC009 */
                           BEGIN
                            /* If not, make a special case and go do it */
                            /* Use the 24 entry in the array to set up a dummy entry */
                            /* This one isn't used for anything else */
                            /* Indicate this is special by passing along a deleted entry - the subroutine will catch it and handle correctly */
                            ext_table[j][23].sys_id = uc(0);            /* AC000 */
                            ext_table[j][23].start_cyl = part_table[j][extended_index].start_cyl;
                            ext_table[j][23].start_head = uc(0);        /* AC000 */
                            ext_table[j][23].start_sector = uc(1);      /* AC000 */

                            /* Write out our modified first location - only pointer info will be sent to the disk*/
                            write_ext_boot_to_disk(c(23),j);            /* AC000 */
                           END
                       END
                   END
               END
           END
        cur_disk = temp_disk;
        return;
END

/*  */
char write_master_boot_to_disk(disk)

unsigned char   disk;

BEGIN

unsigned        char i;
unsigned        j;
unsigned        x;
unsigned        temp;
unsigned long   long_temp;
unsigned        index;
char            location;
unsigned        byte_temp;

        /* Clean out the boot_record */
        for (j=u(0);j < u(BYTES_PER_SECTOR); j++)                       /* AC000 */
           BEGIN
            boot_record[j] = uc(0);                                     /* AC000 */
           END

        /* Copy the master boot record to boot_record */
        for (j=u(0); j < u(BYTES_PER_SECTOR); j++)                      /* AC000 */
           BEGIN
            boot_record[j] = master_boot_record[disk][j];
           END

        /* Copy the partition tables over - only bother with the changed ones */
        for (i=uc(0); i < uc(4); i++)                                   /* AC000 */
           BEGIN
            index = ((unsigned)i)*16;
            if (part_table[disk][i].changed)
               BEGIN
                /* Get boot ind */
                boot_record[0x1BE+(index)] = part_table[disk][i].boot_ind;

                /* Start head */
                boot_record[0x1BF+(index)] = part_table[disk][i].start_head;

                /* Start sector - scramble it to INT 13 format*/
                boot_record[0x1C0+(index)] = (part_table[disk][i].start_sector & 0x3F)  |
                                               ((unsigned char)((part_table[disk][i].start_cyl/256) << 6));

                /* Start cyl - scramble it to INT 13 format*/
                boot_record[0x1C1+(index)] = ((unsigned char)(part_table[disk][i].start_cyl%256));

                /* System id */
                boot_record[0x1C2+(index)]= part_table[disk][i].sys_id;

                /* End head */
                boot_record[0x1C3+(index)] = part_table[disk][i].end_head;

                /* End sector - scramble it to INT 13 format*/
                boot_record[0x1C4+(index)] = (part_table[disk][i].end_sector & 0x3F)  |
                                                ((unsigned char)((part_table[disk][i].end_cyl/256) << 6));

                /* End cyl - scramble it to INT 13 format*/
                boot_record[0x1C5+(index)] = ((unsigned char)(part_table[disk][i].end_cyl%256));

                /* Relative sectors */
                long_temp = part_table[disk][i].rel_sec;
                boot_record[0x1C9+(index)] = uc((long_temp >> 24));                     /* AC000 */
                boot_record[0x1C8+(index)] = uc(((long_temp & 0x00FF0000l) >> 16));     /* AC000 */
                boot_record[0x1C7+(index)] = uc(((long_temp & 0x0000FF00l) >> 8));      /* AC000 */
                boot_record[0x1C6+(index)] = uc((long_temp & 0x000000FFl));             /* AC000 */


                /* Number of sectors */
                long_temp = part_table[disk][i].num_sec;
                boot_record[0x1CD+(index)] = uc(long_temp >> 24);                       /* AC000 */
                boot_record[0x1CC+(index)] = uc((long_temp & 0x00FF0000l) >> 16);       /* AC000 */
                boot_record[0x1CB+(index)] = uc((long_temp & 0x0000FF00l) >> 8);        /* AC000 */
                boot_record[0x1CA+(index)] = uc(long_temp & 0x000000FFl);               /* AC000 */
              END
           END
        boot_record[510] = uc(0x55);                                    /* AC000 */
        boot_record[511] = uc(0xAA);                                    /* AC000 */

        return(write_boot_record(u(0),disk));                           /* AC000 */
END

/*  */
char write_ext_boot_to_disk(entry,disk)

char entry;
unsigned char disk;
BEGIN

char            i;
unsigned        j;
unsigned long   long_temp;
unsigned        index;
char            location;
char            next_drive;
char            pointer;
char            write;

        /* Clean out the boot_record */
        for (j=u(0);j < u(BYTES_PER_SECTOR); j++)                       /* AC000 */
           BEGIN
            boot_record[j] = uc(0);                                     /* AC000 */
           END

        /* First - setup the logical devices */
        /* See if it has been deleted - if so, leave entries as zero */
        /* Otherwise - go unscramble everything out of the arrays */

        if (ext_table[disk][sort[entry]].sys_id != uc(0))               /* AC000 */
           BEGIN
            /* Get boot ind */
            boot_record[0x1BE] = ext_table[disk][sort[entry]].boot_ind;

            /* Start head */
            boot_record[0x1BF] = ext_table[disk][sort[entry]].start_head;

            /* Start sector - scramble it to INT 13 format*/
           boot_record[0x1C0] = (ext_table[disk][sort[entry]].start_sector & 0x3F) |
                    ((ext_table[disk][sort[entry]].start_cyl/256) << 6);

            /* Start cyl - scramble it to INT 13 format*/
            boot_record[0x1C1] = ((unsigned char)(ext_table[disk][sort[entry]].start_cyl%256));

            /* System id */
            boot_record[0x1C2]= ext_table[disk][sort[entry]].sys_id;

            /* End head */
            boot_record[0x1C3] = ext_table[disk][sort[entry]].end_head;

            /* End sector - scramble it to INT 13 format*/
            boot_record[0x1C4] = (ext_table[disk][sort[entry]].end_sector & 0x3F) |
                  ((ext_table[disk][sort[entry]].end_cyl/256) << 6);

            /* End cyl - scramble it to INT 13 format*/
            boot_record[0x1C5] = ((unsigned char)(ext_table[disk][sort[entry]].end_cyl%256));

            /* Relative sectors */
            long_temp = ext_table[disk][sort[entry]].rel_sec;
            boot_record[0x1C9] = uc((long_temp >> 24));                 /* AC000 */
            boot_record[0x1C8] = uc(((long_temp & 0x00FF0000l) >> 16)); /* AC000 */
            boot_record[0x1C7] = uc(((long_temp & 0x0000FF00l) >> 8));  /* AC000 */
            boot_record[0x1C6] = uc((long_temp & 0x000000FFl));         /* AC000 */

            /* Number of sectors */
            long_temp = ext_table[disk][sort[entry]].num_sec;
            boot_record[0x1CD] = uc((long_temp >> 24));                 /* AC000 */
            boot_record[0x1CC] = uc(((long_temp & 0x00FF0000l) >> 16)); /* AC000 */
            boot_record[0x1CB] = uc(((long_temp & 0x0000FF00l) >> 8));  /* AC000 */
            boot_record[0x1CA] = uc((long_temp & 0x000000FFl));         /* AC000 */
           END

        /* set up pointer to next logical drive unless this is # 23 */
        if (entry != c(22))                                             /* AC000 */
           BEGIN
           /* Find the drive to be pointed to */
           pointer = entry+1;

           /* Handle the special case of a deleted or empty first entry in partition*/
           if (entry == c(23))                                          /* AC000 */
              BEGIN
               pointer = c(0);                                          /* AC000 */
              END
           for (i = pointer; i <c(23); i++)                             /* AC000 */
              BEGIN
               next_drive = ((char)(INVALID));

               /* Go look for the next valid drive */
               if (ext_table[disk][sort[i]].sys_id != uc(0))            /* AC000 */
                  BEGIN
                   next_drive = sort[i];
                   break;
                  END
              END
            if (next_drive != ((char)(INVALID)))
               BEGIN
                /* Get boot ind */
                boot_record[0x1CE] = uc(0);                             /* AC000 */

                /* Start head */
                boot_record[0x1CF] = uc(0);                             /* AC000 */

                /* Start sector - scramble it to INT 13 format*/
                boot_record[0x1D0] = uc(0x01) | ((ext_table[disk][next_drive].start_cyl/256) << 6);  /* AC000 */


                /* System id */
                boot_record[0x1D2]= uc(EXTENDED);                       /* AC000 */

                /* End head */
                boot_record[0x1D3] = uc(max_head[disk] -1);             /* AC004 */

                /* End sector - scramble it to INT 13 format*/
                boot_record[0x1D4] =(max_sector[disk] & 0x3F) | ((ext_table[disk][next_drive].end_cyl/256) << 6);


                /* Start cyl - scramble it to INT 13 format*/
                boot_record[0x1D1] = ((unsigned char)(ext_table[disk][next_drive].start_cyl%256));

                /* End cyl - scramble it to INT 13 format*/
                boot_record[0x1D5] = ((unsigned char)(ext_table[disk][next_drive].end_cyl%256));

                /* Relative sectors - this is from the front of the extended volume */
                /* Find the extended partition */
                location = find_partition_location(uc(EXTENDED));
                long_temp = ((unsigned long)(ext_table[disk][next_drive].start_cyl - part_table[disk][location].start_cyl))
                              * max_head[disk] *  max_sector[disk];
                boot_record[0x1D9] = uc((long_temp >> 24));                   /* AC000 */
                boot_record[0x1D8] = uc(((long_temp & 0x00FF0000l) >> 16));   /* AC000 */
                boot_record[0x1D7] = uc(((long_temp & 0x0000FF00l) >> 8));    /* AC000 */
                boot_record[0x1D6] = uc((long_temp & 0x000000FFl));           /* AC000 */

                /* Number of sectors in the next volume*/
                long_temp = ((unsigned long)(ext_table[disk][next_drive].end_cyl - ext_table[disk][next_drive].start_cyl+1))
                            * max_head[disk] * max_sector[disk];
                boot_record[0x1DD] = uc((long_temp >> 24));                   /* AC000 */
                boot_record[0x1DC] = uc(((long_temp & 0x00FF0000l) >> 16));   /* AC000 */
                boot_record[0x1DB] = uc(((long_temp & 0x0000FF00l) >> 8));    /* AC000 */
                boot_record[0x1DA] = uc((long_temp & 0x000000FFl));           /* AC000 */
               END
           END
        boot_record[510] = uc(0x55);                                    /* AC000 */
        boot_record[511] = uc(0xAA);                                    /* AC000 */

        /* Write the boot record out */
        if (entry != c(23))                                             /* AC000 */
           BEGIN
            write = write_boot_record(ext_table[disk][sort[entry]].start_cyl,disk);
           END
         else
            BEGIN
             /* Write the special case of the first entry only having a pointer */
             write = write_boot_record(ext_table[disk][23].start_cyl,disk);
            END
         return(write);
END