Exemplo n.º 1
0
int git_index_write(git_index *index)
{
	git_filebuf file;
	struct stat indexst;
	int error;

	git_vector_sort(&index->entries);

	if ((error = git_filebuf_open(&file, index->index_file_path, GIT_FILEBUF_HASH_CONTENTS)) < GIT_SUCCESS)
		return git__rethrow(error, "Failed to write index");

	if ((error = write_index(index, &file)) < GIT_SUCCESS) {
		git_filebuf_cleanup(&file);
		return git__rethrow(error, "Failed to write index");
	}

	if ((error = git_filebuf_commit(&file)) < GIT_SUCCESS)
		return git__rethrow(error, "Failed to write index");

	if (p_stat(index->index_file_path, &indexst) == 0) {
		index->last_modified = indexst.st_mtime;
		index->on_disk = 1;
	}

	return GIT_SUCCESS;
}
Exemplo n.º 2
0
int git_filebuf_write(git_filebuf *file, const void *buff, size_t len)
{
    int error;
    const unsigned char *buf = buff;

    for (;;) {
        size_t space_left = file->buf_size - file->buf_pos;

        /* cache if it's small */
        if (space_left > len) {
            add_to_cache(file, buf, len);
            return GIT_SUCCESS;
        }

        /* flush the cache if it doesn't fit */
        if (file->buf_pos > 0) {
            add_to_cache(file, buf, space_left);

            if ((error = flush_buffer(file)) < GIT_SUCCESS)
                return git__rethrow(error, "Failed to write to buffer");

            len -= space_left;
            buf += space_left;
        }

        /* write too-large chunks immediately */
        if (len > file->buf_size) {
            error = file->write(file, buf, len);
            if (error < GIT_SUCCESS)
                return git__rethrow(error, "Failed to write to buffer");
        }
    }
}
Exemplo n.º 3
0
/*
 * In this first version, we push all our refs in and start sending
 * them out. When we get an ACK we hide that commit and continue
 * traversing until we're done
 */
int git_fetch_negotiate(git_remote *remote)
{
	int error;
	git_headarray *list = &remote->refs;
	git_transport *t = remote->transport;

	error = filter_wants(remote);
	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to filter the reference list for wants");

	/* Don't try to negotiate when we don't want anything */
	if (list->len == 0)
		return GIT_SUCCESS;
	if (!remote->need_pack)
		return GIT_SUCCESS;

	/*
	 * Now we have everything set up so we can start tell the server
	 * what we want and what we have.
	 */
	error = t->send_wants(t, list);
	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to send want list");

	return t->negotiate_fetch(t, remote->repo, &remote->refs);
}
Exemplo n.º 4
0
static int write_index(git_index *index, git_filebuf *file)
{
	int error = GIT_SUCCESS;
	git_oid hash_final;

	struct index_header header;

	int is_extended;

	assert(index && file);

	is_extended = is_index_extended(index);

	header.signature = htonl(INDEX_HEADER_SIG);
	header.version = htonl(is_extended ? INDEX_VERSION_NUMBER_EXT : INDEX_VERSION_NUMBER);
	header.entry_count = htonl(index->entries.length);

	git_filebuf_write(file, &header, sizeof(struct index_header));

	error = write_entries(index, file);
	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to write index");

	/* TODO: write extensions (tree cache) */

	/* get out the hash for all the contents we've appended to the file */
	git_filebuf_hash(&hash_final, file);

	/* write it at the end of the file */
	git_filebuf_write(file, hash_final.id, GIT_OID_RAWSZ);

	return error == GIT_SUCCESS ? GIT_SUCCESS : git__rethrow(error, "Failed to write index");
}
Exemplo n.º 5
0
static int filter_wants(git_remote *remote)
{
	git_vector list;
	git_headarray refs;
	git_transport *t = remote->transport;
	git_repository *repo = remote->repo;
	const git_refspec *spec;
	int error;
	unsigned int i;

	error = git_vector_init(&list, 16, NULL);
	if (error < GIT_SUCCESS)
		return error;

	error = t->ls(t, &refs);
	if (error < GIT_SUCCESS) {
		error = git__rethrow(error, "Failed to get remote ref list");
		goto cleanup;
	}

	spec = git_remote_fetchspec(remote);
	if (spec == NULL) {
		error = git__throw(GIT_ERROR, "The remote has no fetchspec");
		goto cleanup;
	}

	for (i = 0; i < refs.len; ++i) {
		git_remote_head *head = refs.heads[i];

		/* If it doesn't match the refpec, we don't want it */
		error = git_refspec_src_match(spec, head->name);
		if (error == GIT_ENOMATCH)
			continue;
		if (error < GIT_SUCCESS) {
			error = git__rethrow(error, "Error matching remote ref name");
			goto cleanup;
		}

		/* If we have the object, mark it so we don't ask for it */
		if (git_odb_exists(repo->db, &head->oid))
			head->local = 1;
		else
			remote->need_pack = 1;

		error = git_vector_insert(&list, head);
		if (error < GIT_SUCCESS)
			goto cleanup;
	}

	remote->refs.len = list.length;
	remote->refs.heads = (git_remote_head **) list.contents;

	return GIT_SUCCESS;

cleanup:
	git_vector_free(&list);
	return error;
}
Exemplo n.º 6
0
static int pack_entry_find_prefix(
	struct git_pack_entry *e,
	struct pack_backend *backend,
	const git_oid *short_oid,
	unsigned int len)
{
	int error;
	size_t i;
	unsigned found = 0;

	if ((error = packfile_refresh_all(backend)) < GIT_SUCCESS)
		return git__rethrow(error, "Failed to find pack entry");

	if (backend->last_found) {
		error = git_pack_entry_find(e, backend->last_found, short_oid, len);
		if (error == GIT_EAMBIGUOUSOIDPREFIX) {
			return git__rethrow(error, "Failed to find pack entry. Ambiguous sha1 prefix");
		} else if (error == GIT_SUCCESS) {
			found = 1;
		}
	}

	for (i = 0; i < backend->packs.length; ++i) {
		struct git_pack_file *p;

		p = git_vector_get(&backend->packs, i);
		if (p == backend->last_found)
			continue;

		error = git_pack_entry_find(e, p, short_oid, len);
		if (error == GIT_EAMBIGUOUSOIDPREFIX) {
			return git__rethrow(error, "Failed to find pack entry. Ambiguous sha1 prefix");
		} else if (error == GIT_SUCCESS) {
			found++;
			if (found > 1)
				break;
			backend->last_found = p;
		}
	}

	if (!found) {
		return git__rethrow(GIT_ENOTFOUND, "Failed to find pack entry");
	} else if (found > 1) {
		return git__rethrow(GIT_EAMBIGUOUSOIDPREFIX, "Failed to find pack entry. Ambiguous sha1 prefix");
	} else {
		return GIT_SUCCESS;
	}

}
Exemplo n.º 7
0
int git_config_add_file(git_config *cfg, git_config_file *file, int priority)
{
	file_internal *internal;
	int error;

	assert(cfg && file);

	if ((error = file->open(file)) < GIT_SUCCESS)
		return git__rethrow(error, "Failed to open config file");

	internal = git__malloc(sizeof(file_internal));
	if (internal == NULL)
		return GIT_ENOMEM;

	internal->file = file;
	internal->priority = priority;

	if (git_vector_insert(&cfg->files, internal) < 0) {
		free(internal);
		return GIT_ENOMEM;
	}

	git_vector_sort(&cfg->files);
	internal->file->cfg = cfg;

	return GIT_SUCCESS;
}
Exemplo n.º 8
0
int git_filebuf_printf(git_filebuf *file, const char *format, ...)
{
    va_list arglist;
    size_t space_left = file->buf_size - file->buf_pos;
    int len, error;

    va_start(arglist, format);
    len = vsnprintf((char *)file->buffer + file->buf_pos, space_left, format, arglist);
    va_end(arglist);

    if (len < 0 || (size_t)len >= space_left) {
        if ((error = flush_buffer(file)) < GIT_SUCCESS)
            return git__rethrow(error, "Failed to output to buffer");

        space_left = file->buf_size - file->buf_pos;

        va_start(arglist, format);
        len = vsnprintf((char *)file->buffer + file->buf_pos, space_left, format, arglist);
        va_end(arglist);

        if (len < 0 || (size_t)len > file->buf_size)
            return GIT_ENOMEM;
    }

    file->buf_pos += len;
    return GIT_SUCCESS;

}
Exemplo n.º 9
0
static int packfile_refresh_all(struct pack_backend *backend)
{
	int error;
	struct stat st;

	if (backend->pack_folder == NULL)
		return GIT_SUCCESS;

	if (p_stat(backend->pack_folder, &st) < 0 || !S_ISDIR(st.st_mode))
		return git__throw(GIT_ENOTFOUND, "Failed to refresh packfiles. Backend not found");

	if (st.st_mtime != backend->pack_folder_mtime) {
		char path[GIT_PATH_MAX];
		strcpy(path, backend->pack_folder);

		/* reload all packs */
		error = git_futils_direach(path, GIT_PATH_MAX, packfile_load__cb, (void *)backend);
		if (error < GIT_SUCCESS)
			return git__rethrow(error, "Failed to refresh packfiles");

		git_vector_sort(&backend->packs);
		backend->pack_folder_mtime = st.st_mtime;
	}

	return GIT_SUCCESS;
}
Exemplo n.º 10
0
int git__percent_decode(git_buf *decoded_out, const char *input)
{
	int len, hi, lo, i, error = GIT_SUCCESS;
	assert(decoded_out && input);

	len = strlen(input);
	git_buf_clear(decoded_out);

	for(i = 0; i < len; i++)
	{
		char c = input[i];

		if (c != '%')
			goto append;

		if (i >= len - 2)
			goto append;

		hi = git__fromhex(input[i + 1]);
		lo = git__fromhex(input[i + 2]);

		if (hi < 0 || lo < 0)
			goto append;

		c = (char)(hi << 4 | lo);
		i += 2;

append:
		error = git_buf_putc(decoded_out, c);
		if (error < GIT_SUCCESS)
			return git__rethrow(error, "Failed to percent decode '%s'.", input);
	}

	return error;
}
Exemplo n.º 11
0
static int packfile_load__cb(void *_data, char *path)
{
	struct pack_backend *backend = (struct pack_backend *)_data;
	struct git_pack_file *pack;
	int error;
	size_t i;

	if (git__suffixcmp(path, ".idx") != 0)
		return GIT_SUCCESS; /* not an index */

	for (i = 0; i < backend->packs.length; ++i) {
		struct git_pack_file *p = git_vector_get(&backend->packs, i);
		if (memcmp(p->pack_name, path, strlen(path) - strlen(".idx")) == 0)
			return GIT_SUCCESS;
	}

	error = git_packfile_check(&pack, path);
	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to load packfile");

	if (git_vector_insert(&backend->packs, pack) < GIT_SUCCESS) {
		free(pack);
		return GIT_ENOMEM;
	}

	return GIT_SUCCESS;
}
Exemplo n.º 12
0
static int pack_entry_find(struct git_pack_entry *e, struct pack_backend *backend, const git_oid *oid)
{
	int error;
	size_t i;

	if ((error = packfile_refresh_all(backend)) < GIT_SUCCESS)
		return git__rethrow(error, "Failed to find pack entry");

	if (backend->last_found &&
		git_pack_entry_find(e, backend->last_found, oid, GIT_OID_HEXSZ) == GIT_SUCCESS)
		return GIT_SUCCESS;

	for (i = 0; i < backend->packs.length; ++i) {
		struct git_pack_file *p;

		p = git_vector_get(&backend->packs, i);
		if (p == backend->last_found)
			continue;

		if (git_pack_entry_find(e, p, oid, GIT_OID_HEXSZ) == GIT_SUCCESS) {
			backend->last_found = p;
			return GIT_SUCCESS;
		}
	}

	return git__throw(GIT_ENOTFOUND, "Failed to find pack entry");
}
Exemplo n.º 13
0
int git_treebuilder_write(git_oid *oid, git_repository *repo, git_treebuilder *bld)
{
	unsigned int i;
	int error;
	git_buf tree = GIT_BUF_INIT;

	assert(bld);

	sort_entries(bld);

	/* Grow the buffer beforehand to an estimated size */
	git_buf_grow(&tree, bld->entries.length * 72);

	for (i = 0; i < bld->entries.length; ++i) {
		git_tree_entry *entry = bld->entries.contents[i];

		if (entry->removed)
			continue;

		git_buf_printf(&tree, "%o ", entry->attr);
		git_buf_put(&tree, entry->filename, entry->filename_len + 1);
		git_buf_put(&tree, (char *)entry->oid.id, GIT_OID_RAWSZ);
	}

	if (git_buf_oom(&tree)) {
		git_buf_free(&tree);
		return git__throw(GIT_ENOMEM, "Not enough memory to build the tree data");
	}

	error = git_odb_write(oid, git_repository_database(repo), tree.ptr, tree.size, GIT_OBJ_TREE);
	git_buf_free(&tree);

	return error == GIT_SUCCESS ? GIT_SUCCESS : git__rethrow(error, "Failed to write tree");
}
Exemplo n.º 14
0
static int filter_ref__cb(git_remote_head *head, void *payload)
{
	struct filter_payload *p = payload;
	int error;

	if (!p->found_head && strcmp(head->name, GIT_HEAD_FILE) == 0) {
		p->found_head = 1;
	} else {
		/* If it doesn't match the refpec, we don't want it */
		error = git_refspec_src_match(p->spec, head->name);

		if (error == GIT_ENOMATCH)
			return GIT_SUCCESS;

		if (error < GIT_SUCCESS)
			return git__rethrow(error, "Error matching remote ref name");
	}

	/* If we have the object, mark it so we don't ask for it */
	if (git_odb_exists(p->odb, &head->oid))
		head->local = 1;
	else
		p->remote->need_pack = 1;

	return git_vector_insert(&p->remote->refs, head);
}
Exemplo n.º 15
0
int git_config_get_int64(git_config *cfg, const char *name, int64_t *out)
{
	const char *value, *num_end;
	int ret;
	int64_t num;

	ret = git_config_get_string(cfg, name, &value);
	if (ret < GIT_SUCCESS)
		return git__rethrow(ret, "Failed to retrieve value for '%s'", name);

	ret = git__strtol64(&num, value, &num_end, 0);
	if (ret < GIT_SUCCESS)
		return git__rethrow(ret, "Failed to convert value for '%s'", name);

	switch (*num_end) {
	case 'g':
	case 'G':
		num *= 1024;
		/* fallthrough */

	case 'm':
	case 'M':
		num *= 1024;
		/* fallthrough */

	case 'k':
	case 'K':
		num *= 1024;

		/* check that that there are no more characters after the
		 * given modifier suffix */
		if (num_end[1] != '\0')
			return git__throw(GIT_EINVALIDTYPE,
				"Failed to get value for '%s'. Invalid type suffix", name);

		/* fallthrough */

	case '\0':
		*out = num;
		return GIT_SUCCESS;

	default:
		return git__throw(GIT_EINVALIDTYPE,
			"Failed to get value for '%s'. Value is of invalid type", name);
	}
}
Exemplo n.º 16
0
int pack_backend__read(void **buffer_p, size_t *len_p, git_otype *type_p, git_odb_backend *backend, const git_oid *oid)
{
	struct git_pack_entry e;
	git_rawobj raw;
	int error;

	if ((error = pack_entry_find(&e, (struct pack_backend *)backend, oid)) < GIT_SUCCESS)
		return git__rethrow(error, "Failed to read pack backend");

	if ((error = git_packfile_unpack(&raw, e.p, &e.offset)) < GIT_SUCCESS)
		return git__rethrow(error, "Failed to read pack backend");

	*buffer_p = raw.data;
	*len_p = raw.len;
	*type_p = raw.type;

	return GIT_SUCCESS;
}
Exemplo n.º 17
0
int git_index_append(git_index *index, const char *path, int stage)
{
	int error;
	git_index_entry entry;

	if ((error = index_init_entry(&entry, index, path, stage)) < GIT_SUCCESS)
		return git__rethrow(error, "Failed to append to index");

	return index_insert(index, &entry, 0);
}
Exemplo n.º 18
0
/*
 * Based on the Android implementation, BSD licensed.
 * Check http://android.git.kernel.org/
 */
int git_path_dirname_r(git_buf *buffer, const char *path)
{
	const char *endp;
	int result, len;

	/* Empty or NULL string gets treated as "." */
	if (path == NULL || *path == '\0') {
		path = ".";
		len = 1;
		goto Exit;
	}

	/* Strip trailing slashes */
	endp = path + strlen(path) - 1;
	while (endp > path && *endp == '/')
		endp--;

	/* Find the start of the dir */
	while (endp > path && *endp != '/')
		endp--;

	/* Either the dir is "/" or there are no slashes */
	if (endp == path) {
		path = (*endp == '/') ? "/" : ".";
		len = 1;
		goto Exit;
	}

	do {
		endp--;
	} while (endp > path && *endp == '/');

	len = endp - path +1;

#ifdef GIT_WIN32
	/* Mimic unix behavior where '/.git' returns '/': 'C:/.git' will return
		'C:/' here */

	if (len == 2 && isalpha(path[0]) && path[1] == ':') {
		len = 3;
		goto Exit;
	}
#endif

Exit:
	result = len;

	if (buffer != NULL) {
		if (git_buf_set(buffer, path, len) < GIT_SUCCESS)
			return git__rethrow(git_buf_lasterror(buffer),
				"Could not get dirname of '%s'", path);
	}

	return result;
}
Exemplo n.º 19
0
static int _rmdir_recurs_foreach(void *opaque, char *path)
{
	int error = GIT_SUCCESS;
	int force = *(int *)opaque;

	if (git_futils_isdir(path) == GIT_SUCCESS) {
		size_t root_size = strlen(path);

		if ((error = git_futils_direach(path, GIT_PATH_MAX, _rmdir_recurs_foreach, opaque)) < GIT_SUCCESS)
			return git__rethrow(error, "Failed to remove directory `%s`", path);

		path[root_size] = '\0';
		return p_rmdir(path);

	} else if (force) {
		return p_unlink(path);
	}

	return git__rethrow(error, "Failed to remove directory. `%s` is not empty", path);
}
Exemplo n.º 20
0
static int local_ls(git_transport *transport, git_headarray *array)
{
	int error;
	unsigned int i;
	git_repository *repo;
	git_vector *vec;
	git_strarray refs;
	transport_local *t = (transport_local *) transport;

	assert(transport && transport->connected);

	repo = t->repo;

	error = git_reference_listall(&refs, repo, GIT_REF_LISTALL);
	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to list remote heads");

	vec = git__malloc(sizeof(git_vector));
	if (vec == NULL) {
		error = GIT_ENOMEM;
		goto out;
	}

	error = git_vector_init(vec, refs.count, NULL);
	if (error < GIT_SUCCESS)
		return error;

	/* Sort the references first */
	qsort(refs.strings, refs.count, sizeof(char *), cmp_refs);

	/* Add HEAD */
	error = add_ref(GIT_HEAD_FILE, repo, vec);
	if (error < GIT_SUCCESS)
		goto out;

	for (i = 0; i < refs.count; ++i) {
		error = add_ref(refs.strings[i], repo, vec);
		if (error < GIT_SUCCESS)
			goto out;
	}

	array->len = vec->length;
	array->heads = (git_remote_head **)vec->contents;

	t->refs = vec;

 out:

	git_strarray_free(&refs);

	return error;
}
Exemplo n.º 21
0
int git_signature_new(git_signature **sig_out, const char *name, const char *email, git_time_t time, int offset)
{
    int error;
    git_signature *p = NULL;

    assert(name && email);

    *sig_out = NULL;

    if ((p = git__malloc(sizeof(git_signature))) == NULL) {
        error = GIT_ENOMEM;
        goto cleanup;
    }

    memset(p, 0x0, sizeof(git_signature));

    error = process_trimming(name, &p->name, name + strlen(name), 1);
    if (error < GIT_SUCCESS) {
        git__rethrow(GIT_EINVALIDARGS, "Failed to create signature. 'name' argument is invalid");
        goto cleanup;
    }

    error = process_trimming(email, &p->email, email + strlen(email), 1);
    if (error < GIT_SUCCESS) {
        git__rethrow(GIT_EINVALIDARGS, "Failed to create signature. 'email' argument is invalid");
        goto cleanup;
    }

    p->when.time = time;
    p->when.offset = offset;

    *sig_out = p;

    return error;

cleanup:
    git_signature_free(p);
    return error;
}
Exemplo n.º 22
0
int git_index_read(git_index *index)
{
	struct stat indexst;
	int error = GIT_SUCCESS;

	assert(index->index_file_path);

	if (!index->on_disk || git_futils_exists(index->index_file_path) < 0) {
		git_index_clear(index);
		index->on_disk = 0;
		return GIT_SUCCESS;
	}

	if (p_stat(index->index_file_path, &indexst) < 0)
		return git__throw(GIT_EOSERR, "Failed to read index. %s does not exist or is corrupted", index->index_file_path);

	if (!S_ISREG(indexst.st_mode))
		return git__throw(GIT_ENOTFOUND, "Failed to read index. %s is not an index file", index->index_file_path);

	if (indexst.st_mtime != index->last_modified) {

		git_fbuffer buffer;

		if ((error = git_futils_readbuffer(&buffer, index->index_file_path)) < GIT_SUCCESS)
			return git__rethrow(error, "Failed to read index");

		git_index_clear(index);
		error = parse_index(index, buffer.data, buffer.len);

		if (error == GIT_SUCCESS)
			index->last_modified = indexst.st_mtime;

		git_futils_freebuffer(&buffer);
	}

	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to read index");
	return error;
}
Exemplo n.º 23
0
int pack_backend__read_prefix(
	git_oid *out_oid,
	void **buffer_p,
	size_t *len_p,
	git_otype *type_p,
	git_odb_backend *backend,
	const git_oid *short_oid,
	unsigned int len)
{
	if (len < GIT_OID_MINPREFIXLEN)
		return git__throw(GIT_EAMBIGUOUSOIDPREFIX, "Failed to read pack backend. Prefix length is lower than %d.", GIT_OID_MINPREFIXLEN);

	if (len >= GIT_OID_HEXSZ) {
		/* We can fall back to regular read method */
		int error = pack_backend__read(buffer_p, len_p, type_p, backend, short_oid);
		if (error == GIT_SUCCESS)
			git_oid_cpy(out_oid, short_oid);

		return error;
	} else {
		struct git_pack_entry e;
		git_rawobj raw;
		int error;

		if ((error = pack_entry_find_prefix(&e, (struct pack_backend *)backend, short_oid, len)) < GIT_SUCCESS)
			return git__rethrow(error, "Failed to read pack backend");

		if ((error = git_packfile_unpack(&raw, e.p, &e.offset)) < GIT_SUCCESS)
			return git__rethrow(error, "Failed to read pack backend");

		*buffer_p = raw.data;
		*len_p = raw.len;
		*type_p = raw.type;
		git_oid_cpy(out_oid, &e.sha1);
	}

	return GIT_SUCCESS;
}
Exemplo n.º 24
0
static int tree_parse_buffer(git_tree *tree, const char *buffer, const char *buffer_end)
{
	int error = GIT_SUCCESS;

	if (git_vector_init(&tree->entries, DEFAULT_TREE_SIZE, entry_sort_cmp) < GIT_SUCCESS)
		return GIT_ENOMEM;

	while (buffer < buffer_end) {
		git_tree_entry *entry;
		int tmp;

		entry = git__calloc(1, sizeof(git_tree_entry));
		if (entry == NULL) {
			error = GIT_ENOMEM;
			break;
		}

		if (git_vector_insert(&tree->entries, entry) < GIT_SUCCESS)
			return GIT_ENOMEM;

		if (git__strtol32(&tmp, buffer, &buffer, 8) < GIT_SUCCESS ||
			!buffer || !valid_attributes(tmp))
			return git__throw(GIT_EOBJCORRUPTED, "Failed to parse tree. Can't parse attributes");

		entry->attr = tmp;

		if (*buffer++ != ' ') {
			error = git__throw(GIT_EOBJCORRUPTED, "Failed to parse tree. Object it corrupted");
			break;
		}

		if (memchr(buffer, 0, buffer_end - buffer) == NULL) {
			error = git__throw(GIT_EOBJCORRUPTED, "Failed to parse tree. Object it corrupted");
			break;
		}

		entry->filename = git__strdup(buffer);
		entry->filename_len = strlen(buffer);

		while (buffer < buffer_end && *buffer != 0)
			buffer++;

		buffer++;

		git_oid_fromraw(&entry->oid, (const unsigned char *)buffer);
		buffer += GIT_OID_RAWSZ;
	}

	return error == GIT_SUCCESS ? GIT_SUCCESS : git__rethrow(error, "Failed to parse buffer");
}
Exemplo n.º 25
0
int git_config_get_bool(git_config *cfg, const char *name, int *out)
{
	const char *value;
	int error = GIT_SUCCESS;

	error = git_config_get_string(cfg, name, &value);
	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to get value for %s", name);

	/* A missing value means true */
	if (value == NULL) {
		*out = 1;
		return GIT_SUCCESS;
	}

	if (!strcasecmp(value, "true") ||
		!strcasecmp(value, "yes") ||
		!strcasecmp(value, "on")) {
		*out = 1;
		return GIT_SUCCESS;
	}
	if (!strcasecmp(value, "false") ||
		!strcasecmp(value, "no") ||
		!strcasecmp(value, "off")) {
		*out = 0;
		return GIT_SUCCESS;
	}

	/* Try to parse it as an integer */
	error = git_config_get_int32(cfg, name, out);
	if (error == GIT_SUCCESS)
		*out = !!(*out);

	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to get value for %s", name);
	return error;
}
Exemplo n.º 26
0
int git_filebuf_hash(git_oid *oid, git_filebuf *file)
{
    int error;

    assert(oid && file && file->digest);

    if ((error = flush_buffer(file)) < GIT_SUCCESS)
        return git__rethrow(error, "Failed to get hash for file");

    git_hash_final(oid, file->digest);
    git_hash_free_ctx(file->digest);
    file->digest = NULL;

    return GIT_SUCCESS;
}
Exemplo n.º 27
0
int git_tree_create_fromindex(git_oid *oid, git_index *index)
{
	int error;

	if (index->repository == NULL)
		return git__throw(GIT_EBAREINDEX, "Failed to create tree. The index file is not backed up by an existing repository");

	if (index->tree != NULL && index->tree->entries >= 0) {
		git_oid_cpy(oid, &index->tree->oid);
		return GIT_SUCCESS;
	}

	/* The tree cache didn't help us */
	error = write_tree(oid, index, "", 0);
	return (error < GIT_SUCCESS) ? git__rethrow(error, "Failed to create tree") : GIT_SUCCESS;
}
Exemplo n.º 28
0
int git_config_get_int32(git_config *cfg, const char *name, int32_t *out)
{
	int64_t tmp_long;
	int32_t tmp_int;
	int ret;

	ret = git_config_get_int64(cfg, name, &tmp_long);
	if (ret < GIT_SUCCESS)
		return git__rethrow(ret, "Failed to convert value for '%s'", name);
	
	tmp_int = tmp_long & 0xFFFFFFFF;
	if (tmp_int != tmp_long)
		return git__throw(GIT_EOVERFLOW, "Value for '%s' is too large", name);

	*out = tmp_int;

	return ret;
}
Exemplo n.º 29
0
/*
 * Based on the Android implementation, BSD licensed.
 * Check http://android.git.kernel.org/
 */
int git_path_basename_r(git_buf *buffer, const char *path)
{
	const char *endp, *startp;
	int len, result;

	/* Empty or NULL string gets treated as "." */
	if (path == NULL || *path == '\0') {
		startp = ".";
		len		= 1;
		goto Exit;
	}

	/* Strip trailing slashes */
	endp = path + strlen(path) - 1;
	while (endp > path && *endp == '/')
		endp--;

	/* All slashes becomes "/" */
	if (endp == path && *endp == '/') {
		startp = "/";
		len	= 1;
		goto Exit;
	}

	/* Find the start of the base */
	startp = endp;
	while (startp > path && *(startp - 1) != '/')
		startp--;

	len = endp - startp +1;

Exit:
	result = len;

	if (buffer != NULL) {
		if (git_buf_set(buffer, startp, len) < GIT_SUCCESS)
			return git__rethrow(git_buf_lasterror(buffer),
				"Could not get basename of '%s'", path);
	}

	return result;
}
Exemplo n.º 30
0
int git_transport_new(git_transport **out, const char *url)
{
	git_transport_cb fn;
	git_transport *transport;
	int error;

	fn = transport_new_fn(url);

	error = fn(&transport);
	if (error < GIT_SUCCESS)
		return git__rethrow(error, "Failed to create new transport");

	transport->url = git__strdup(url);
	if (transport->url == NULL)
		return GIT_ENOMEM;

	*out = transport;

	return GIT_SUCCESS;
}