Beispiel #1
0
/** \internal
 * Copy the contents of one directory structure to another.
 * Note that this currently does not copy the FS_FILE info.
 * It is only used to make a copy of the orphan directory.
 * It does not check for duplicate entries.
 * @returns 1 on error
 */
static uint8_t
tsk_fs_dir_copy(const TSK_FS_DIR * a_src_dir, TSK_FS_DIR * a_dst_dir)
{
    size_t i;

    a_dst_dir->names_used = 0;

    // make sure we got the room
    if (a_src_dir->names_used > a_dst_dir->names_alloc) {
        if (tsk_fs_dir_realloc(a_dst_dir, a_src_dir->names_used))
            return 1;
    }

    for (i = 0; i < a_src_dir->names_used; i++) {
        if (tsk_fs_name_copy(&a_dst_dir->names[i], &a_src_dir->names[i]))
            return 1;
    }

    a_dst_dir->names_used = a_src_dir->names_used;
    a_dst_dir->addr = a_src_dir->addr;
    return 0;
}
Beispiel #2
0
/** \internal
 * Add a FS_DENT structure to a FS_DIR structure by copying its
 * contents into the internal buffer. Checks for
 * duplicates and expands buffer as needed.
 * @param a_fs_dir DIR to add to
 * @param a_fs_name DENT to add
 * @returns 1 on error (memory allocation problems) and 0 on success
 */
uint8_t
tsk_fs_dir_add(TSK_FS_DIR * a_fs_dir, const TSK_FS_NAME * a_fs_name)
{
    TSK_FS_NAME *fs_name_dest = NULL;
    size_t i;

    /* see if we already have it in the buffer / queue
     * We skip this check for FAT because it will always fail because two entries
     * never have the same meta address. */
    // @@@ We could do something more effecient here too with orphan files because we do not 
    // need to check the contents of that directory either and this takes a lot of time on those
    // large images.
	if (TSK_FS_TYPE_ISFAT(a_fs_dir->fs_info->ftype) == 0) {
		for (i = 0; i < a_fs_dir->names_used; i++) {
			if ((a_fs_name->meta_addr == a_fs_dir->names[i].meta_addr) &&
				(strcmp(a_fs_name->name, a_fs_dir->names[i].name) == 0)) {

				if (tsk_verbose)
					tsk_fprintf(stderr,
						"tsk_fs_dir_add: removing duplicate entry: %s (%"
						PRIuINUM ")\n", a_fs_name->name, a_fs_name->meta_addr);

				/* We do not check type because then we cannot detect NTFS orphan file
				 * duplicates that are added as "-/r" while a similar entry exists as "r/r"
				 (a_fs_name->type == a_fs_dir->names[i].type)) { */

				// if the one in the list is unalloc and we have an alloc, replace it
				if ((a_fs_dir->names[i].flags & TSK_FS_NAME_FLAG_UNALLOC) &&
					(a_fs_name->flags & TSK_FS_NAME_FLAG_ALLOC)) {
					fs_name_dest = &a_fs_dir->names[i];

					// free the memory - not the most effecient, but prevents
					// duplicate code.
					if (fs_name_dest->name) {
						free(fs_name_dest->name);
						fs_name_dest->name = NULL;
						fs_name_dest->name_size = 0;
					}
					if (fs_name_dest->shrt_name) {
						free(fs_name_dest->shrt_name);
						fs_name_dest->shrt_name = NULL;
						fs_name_dest->shrt_name_size = 0;
					}
					break;
				}
				else {
					return 0;
				}
			}
		}
	}

    if (fs_name_dest == NULL) {
        // make sure we got the room
        if (a_fs_dir->names_used >= a_fs_dir->names_alloc) {
            if (tsk_fs_dir_realloc(a_fs_dir, a_fs_dir->names_used + 512))
                return 1;
        }

        fs_name_dest = &a_fs_dir->names[a_fs_dir->names_used++];
    }

    if (tsk_fs_name_copy(fs_name_dest, a_fs_name))
        return 1;

    // add the parent address
    if (a_fs_dir->addr)
        fs_name_dest->par_addr = a_fs_dir->addr;

    return 0;
}
Beispiel #3
0
/** \internal
 * Add a FS_DENT structure to a FS_DIR structure by copying its
 * contents into the internal buffer. Checks for
 * duplicates and expands buffer as needed.
 * @param a_fs_dir DIR to add to
 * @param a_fs_name DENT to add
 * @returns 1 on error (memory allocation problems) and 0 on success
 */
uint8_t
tsk_fs_dir_add(TSK_FS_DIR * a_fs_dir, const TSK_FS_NAME * a_fs_name)
{
    TSK_FS_NAME *fs_name_dest = NULL;
    size_t i;

    // see if we already have it in the buffer / queue
    for (i = 0; i < a_fs_dir->names_used; i++) {
        if ((a_fs_name->meta_addr == a_fs_dir->names[i].meta_addr) &&
            (strcmp(a_fs_name->name, a_fs_dir->names[i].name) == 0)) {

            if (tsk_verbose)
                tsk_fprintf(stderr,
                    "tsk_fs_dir_add: removing duplicate entry: %s (%"
                    PRIuINUM ")\n", a_fs_name->name, a_fs_name->meta_addr);

            /* We do not check type because then we cannot detect NTFS orphan file
             * duplicates that are added as "-/r" while a similar entry exists as "r/r"
             (a_fs_name->type == a_fs_dir->names[i].type)) { */

            // if the one in the list is unalloc and we have an alloc, replace it
            if ((a_fs_dir->names[i].flags & TSK_FS_NAME_FLAG_UNALLOC) &&
                (a_fs_name->flags & TSK_FS_NAME_FLAG_ALLOC)) {
                fs_name_dest = &a_fs_dir->names[i];

                // free the memory - not the most effecient, but prevents
                // duplicate code.
                if (fs_name_dest->name) {
                    free(fs_name_dest->name);
                    fs_name_dest->name = NULL;
                    fs_name_dest->name_size = 0;
                }
                if (fs_name_dest->shrt_name) {
                    free(fs_name_dest->shrt_name);
                    fs_name_dest->shrt_name = NULL;
                    fs_name_dest->shrt_name_size = 0;
                }
                break;
            }
            else {
                return 0;
            }
        }
    }

    if (fs_name_dest == NULL) {
        // make sure we got the room
        if (a_fs_dir->names_used >= a_fs_dir->names_alloc) {
            if (tsk_fs_dir_realloc(a_fs_dir, a_fs_dir->names_used + 256))
                return 1;
        }

        fs_name_dest = &a_fs_dir->names[a_fs_dir->names_used++];
    }

    if (tsk_fs_name_copy(fs_name_dest, a_fs_name))
        return 1;

    // add the parent address
    if (a_fs_dir->addr)
        fs_name_dest->par_addr = a_fs_dir->addr;

    return 0;
}