示例#1
0
image_contents_t *diskcontents_block_read(vdrive_t *vdrive)
{
    image_contents_t *contents;
    BYTE buffer[256];
    int retval;
    image_contents_file_list_t *lp;

    machine_drive_flush();

    if (vdrive == NULL)
        return NULL;

    retval = vdrive_bam_read_bam(vdrive);

    if (retval < 0) {
        vdrive_internal_close_disk_image(vdrive);
        return NULL;
    }

    contents = image_contents_new();

    memcpy(contents->name, vdrive->bam + vdrive->bam_name,
           IMAGE_CONTENTS_NAME_LEN);
    contents->name[IMAGE_CONTENTS_NAME_LEN] = 0;

    memcpy(contents->id, vdrive->bam + vdrive->bam_id, IMAGE_CONTENTS_ID_LEN);
    contents->id[IMAGE_CONTENTS_ID_LEN] = 0;

    contents->blocks_free = (int)vdrive_bam_free_block_count(vdrive);

    vdrive->Curr_track = vdrive->Dir_Track;
    vdrive->Curr_sector = vdrive->Dir_Sector;

    lp = NULL;
    contents->file_list = NULL;

    circular_check_init();

    while (1) {
        BYTE *p;
        int j;

        retval = vdrive_read_sector(vdrive, buffer,
                                        vdrive->Curr_track,
                                        vdrive->Curr_sector);

        if (retval != 0
            || circular_check(vdrive->Curr_track, vdrive->Curr_sector)) {
            /*image_contents_destroy(contents);*/
            vdrive_internal_close_disk_image(vdrive);
            circular_check_free();
            return contents/*NULL*/;
        }

        for (p = buffer, j = 0; j < 8; j++, p += 32)
            if (p[SLOT_TYPE_OFFSET] != 0) {
                image_contents_file_list_t *new_list;
                int i;

                new_list = lib_malloc(sizeof(image_contents_file_list_t));
                new_list->size = ((int)p[SLOT_NR_BLOCKS]
                                  + ((int)p[SLOT_NR_BLOCKS + 1] << 8));

                for (i = 0; i < IMAGE_CONTENTS_FILE_NAME_LEN; i++)
                        new_list->name[i] = p[SLOT_NAME_OFFSET + i];

                new_list->name[IMAGE_CONTENTS_FILE_NAME_LEN] = 0;

                new_list->name[i] = 0;

                sprintf((char *)new_list->type, "%c%s%c",
                        (p[SLOT_TYPE_OFFSET] & CBMDOS_FT_CLOSED ? ' ' : '*'),
                        cbmdos_filetype_get(p[SLOT_TYPE_OFFSET] & 0x07),
                        (p[SLOT_TYPE_OFFSET] & CBMDOS_FT_LOCKED ? '<' : ' '));

                new_list->next = NULL;

                if (lp == NULL) {
                    new_list->prev = NULL;
                    contents->file_list = new_list;
                    lp = contents->file_list;
                } else {
                    new_list->prev = lp;
                    lp->next = new_list;
                    lp = new_list;
                }
            }

        if (buffer[0] == 0)
            break;

        vdrive->Curr_track = (int)buffer[0];
        vdrive->Curr_sector = (int)buffer[1];
    }

    vdrive_internal_close_disk_image(vdrive);
    circular_check_free();
    return contents;
}
示例#2
0
int vdrive_dir_next_directory(vdrive_t *vdrive, bufferinfo_t *b)
{
    BYTE *l, *p;
    int blocks, i;

    while ((p = vdrive_dir_find_next_slot(&b->dir))) {
        if (p[SLOT_TYPE_OFFSET]) {
            l = b->buffer + b->bufptr;

            *l++ = 1;
            *l++ = 1;

            /*
             * Length and spaces
             */
            *l++ = p[SLOT_NR_BLOCKS];
            *l++ = p[SLOT_NR_BLOCKS + 1];

            memset(l, 32, 27);
            l[27] = 0;

            blocks = p[SLOT_NR_BLOCKS] + p[SLOT_NR_BLOCKS + 1] * 256;

            if (blocks < 10) {
                l++;
            }
            if (blocks < 100) {
                l++;
            }
            l++;

            *l++ = '"';

            memcpy(l, &p[SLOT_NAME_OFFSET], 16);

            for (i = 0; (i < 16) && (p[SLOT_NAME_OFFSET + i] != 0xa0); ) {
                i++;
            }

            vdrive_dir_no_a0_pads(l, 16);

            l[i] = '"';

            /*
             * Type + End
             * There are 3 spaces or < and 2 spaces after the filetype.
             * Well, not exactly - the whole directory entry is 32 byte long
             * (including nullbyte).
             * Depending on the file size, there are more or less spaces
             */

            l[17] = (p[SLOT_TYPE_OFFSET] & CBMDOS_FT_CLOSED) ? ' ' : '*';
            memcpy(l + 18, cbmdos_filetype_get(p[SLOT_TYPE_OFFSET] & 0x07), 3);
            l[21] = (p[SLOT_TYPE_OFFSET] & CBMDOS_FT_LOCKED) ? '<' : ' ';

            b->bufptr = (b->bufptr + 32) & 255;

            if (b->bufptr == 0) {
                return 0;
            }
        }
    }

    blocks = vdrive_bam_free_block_count(vdrive);

    l = b->buffer + b->bufptr;
    *l++ = 1;
    *l++ = 1;
    *l++ = blocks;
    *l++ = blocks >> 8;
    memcpy(l, "BLOCKS FREE.", 12);
    memset(l + 12, 32, 13);
    l[25] = 0;
    l[26] = 0;
    l[27] = 0;
    return b->bufptr + 31;
}
示例#3
0
int vdrive_dir_create_directory(vdrive_t *vdrive, const char *name,
                                int length, int filetype, BYTE *outputptr)
{
    BYTE *l, *p;
    BYTE *origptr = outputptr;
    int blocks, i;

    if (length) {
        if (*name == '$') {
            ++name;
            --length;
        }
        if (*name == ':') {
            ++name;
            --length;
        }
    }
    if (!*name || length < 1) {
        name = "*\0";
        length = 1;
    }

    /*
     * Start Address, Line Link and Line number 0
     */

    l = outputptr;
    *l++ = 1;
    *l++ = 4;

    l += 2;                     /* Leave space for Next Line Link */
    *l++ = 0;
    *l++ = 0;

    *l++ = (BYTE)0x12;          /* Reverse on */

    *l++ = '"';

    memcpy(l, &vdrive->bam[vdrive->bam_name], 16);
    vdrive_dir_no_a0_pads(l, 16);
    l += 16;
    *l++ = '"';
    *l++ = ' ';
    memcpy(l, &vdrive->bam[vdrive->bam_id], 5);
    vdrive_dir_no_a0_pads(l, 5);
    l += 5;
    *l++ = 0;

    /*
     * Pointer to the next line
     */

    outputptr[2] = 1;
    outputptr[3] = 1;
    outputptr = l;

    /*
     * Now, list files that match the pattern.
     * Wildcards can be used too.
     */

    vdrive_dir_find_first_slot(vdrive, name, length, filetype);

    while ((p = vdrive_dir_find_next_slot(vdrive))) {
        BYTE *tl;

        /* Check whether the directory exceeds the malloced memory.  We make
           sure there is enough space for two lines because we also have to
           add the final ``...BLOCKS FREE'' line.  */
        if ((l - origptr) >= DIR_MAXBUF - 64) {
            log_error(vdrive_dir_log, "Directory too long: giving up.");
            return -1;
        }

        if (p[SLOT_TYPE_OFFSET]) {

            tl = l;
            l += 2;

            /*
             * Length and spaces
             */
            blocks = p[SLOT_NR_BLOCKS] + p[SLOT_NR_BLOCKS + 1] * 256;
            SET_LO_HI(l, blocks);

            if (blocks < 10)
                *l++ = ' ';
            if (blocks < 100)
                *l++ = ' ';
            /*
             * Filename
             */

            *l++ = ' ';
            *l++ = '"';

            memcpy(l, &p[SLOT_NAME_OFFSET], 16);

            for (i = 0; (i < 16) && (p[SLOT_NAME_OFFSET + i] != 0xa0);)
                i++;

            vdrive_dir_no_a0_pads(l, 16);

            l[16] = ' ';
            l[i] = '"';
            l += 17;

            /*
             * Type + End
             * There are 3 spaces or < and 2 spaces after the filetype.
             * Well, not exactly - the whole directory entry is 32 byte long
             * (including nullbyte).
             * Depending on the file size, there are more or less spaces
             */

            sprintf((char *)l, "%c%s%c%c",
                    (p[SLOT_TYPE_OFFSET] & CBMDOS_FT_CLOSED ? ' ' : '*'),
                    cbmdos_filetype_get(p[SLOT_TYPE_OFFSET] & 0x07),
                    (p[SLOT_TYPE_OFFSET] & CBMDOS_FT_LOCKED ? '<' : ' '),
                    0);
            l += 5;
            i = (int)(l - tl);

            while (i < 31) {
                *l++ = ' ';
                i++;
            }
            *l++ = '\0';

            /*
             * New address
             */

            outputptr[0] = 1;
            outputptr[1] = 1;
            outputptr = l;
        }
    }

    blocks = vdrive_bam_free_block_count(vdrive);

    *l++ = 0;
    *l++ = 0;
    SET_LO_HI(l, blocks);
    memcpy(l, "BLOCKS FREE.", 12);
    l += 12;
    memset(l, ' ', 13);
    l += 13;
    *l++ = (char) 0;

    /* Line Address */
    outputptr[0] = 1;
    outputptr[1] = 1;

    /*
     * end
     */
    *l++ = (char) 0;
    *l++ = (char) 0;
    *l   = (char) 0;

    return (int)(l - origptr);
}