libgit2 - 使用Github进行克隆操作

时间:2014-08-08 15:39:55

标签: git github libgit2

我有一段时间让libgit2克隆。这个使用克隆的例子几乎是从他们的文档中逐字记录的。

似乎libgit2在尝试删除' core.symlinks'时崩溃了。它作为克隆的一部分创建的git repo中的键。

有谁知道如何使用libgit2正确克隆github repo。

libgit2 - 稳定 - v0.21.1

#include <git2.h>
#include <unistd.h>
#include <stdio.h>


typedef struct { 
int a;
/* … */ } progress_data;

int fetch_progress(
            const git_transfer_progress *stats,
            void *payload)
{
  progress_data *pd = (progress_data*)payload;

    int fetch_percent =
        (100 * stats->received_objects) /
        stats->total_objects;
    int index_percent =
        (100 * stats->indexed_objects) /
        stats->total_objects;
    int kbytes = stats->received_bytes / 1024;

    printf("network %3d%% (%4d kb, %5d/%5d)  /"
            "  index %3d%% (%5d/%5d)\n",
            fetch_percent, kbytes,
            stats->received_objects, stats->total_objects,
            index_percent,
            stats->indexed_objects, stats->total_objects);

//  printf("in fetch_progress\n");


  /* Do something with network transfer progress */
}



void checkout_progress(
            const char *path,
            size_t cur,
            size_t tot,
            void *payload)
{
  progress_data *pd = (progress_data*)payload;

  printf("in checkout_progress\n");

  /* Do something with checkout progress */
}


int main(void) {

    /* … */
    progress_data d = { 0 };
    git_clone_options clone_opts = GIT_CLONE_OPTIONS_INIT;
    git_checkout_options checkout_opts = GIT_CHECKOUT_OPTIONS_INIT;

    checkout_opts.checkout_strategy = GIT_CHECKOUT_FORCE;
    checkout_opts.progress_cb = checkout_progress;
    checkout_opts.progress_payload = &d;


    clone_opts.checkout_opts = checkout_opts;
    clone_opts.remote_callbacks.transfer_progress = fetch_progress;
//  clone_opts.remote_callbacks.fetch_progress_cb = fetch_progress;
    clone_opts.remote_callbacks.payload = &d;

    git_repository *repo = NULL;

    const char *url = "git://github.com/WigWagCo/twlib";
    const char *path = "tmp";

    int error = git_clone(&repo, url, path, &clone_opts);

    sleep(15);

}

和崩溃:

$ gdb --args ./a.out 
GNU gdb (Ubuntu/Linaro 7.4-2012.04-0ubuntu2.1) 7.4-2012.04
...
(gdb) r
Starting program: /home/ed/work/devicejs/tools/packageTools/a.out 
warning: no loadable sections found in added symbol-file system-supplied DSO at 0x7ffff7ffa000
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".
a.out: ../vendor/libgit2/src/global.c:274: git__global_state: Assertion `git_atomic_get(&git__n_inits) > 0' failed.

Program received signal SIGABRT, Aborted.
0x00007ffff6c8c425 in __GI_raise (sig=<optimized out>) at ../nptl/sysdeps/unix/sysv/linux/raise.c:64
64  ../nptl/sysdeps/unix/sysv/linux/raise.c: No such file or directory.
(gdb) bt
#0  0x00007ffff6c8c425 in __GI_raise (sig=<optimized out>) at ../nptl/sysdeps/unix/sysv/linux/raise.c:64
#1  0x00007ffff6c8fb8b in __GI_abort () at abort.c:91
#2  0x00007ffff6c850ee in __assert_fail_base (fmt=<optimized out>, assertion=0x4bad88 "git_atomic_get(&git__n_inits) > 0", file=0x4bad50 "../vendor/libgit2/src/global.c", line=<optimized out>, function=<optimized out>)
    at assert.c:94
#3  0x00007ffff6c85192 in __GI___assert_fail (assertion=0x4bad88 "git_atomic_get(&git__n_inits) > 0", file=0x4bad50 "../vendor/libgit2/src/global.c", line=274, function=0x4badb0 "git__global_state") at assert.c:103
#4  0x0000000000411cd3 in git__global_state () at ../vendor/libgit2/src/global.c:274
#5  0x000000000040e06a in set_error (error_class=7, string=0x6f8670 "Could not find key 'core.symlinks' to delete") at ../vendor/libgit2/src/errors.c:23
#6  0x000000000040e247 in giterr_set (error_class=7, string=0x4ba350 "Could not find key '%s' to delete") at ../vendor/libgit2/src/errors.c:74
#7  0x000000000040b9da in config_delete (cfg=0x6f8230, name=0x4bc555 "core.symlinks") at ../vendor/libgit2/src/config_file.c:611
#8  0x00000000004082d4 in git_config_delete_entry (cfg=0x6f80a0, name=0x4bc555 "core.symlinks") at ../vendor/libgit2/src/config.c:606
#9  0x000000000041ebc6 in repo_init_fs_configs (cfg=0x6f80a0, cfg_path=0x6f8190 "/home/ed/work/devicejs/tools/packageTools/tmp/.git/config", repo_dir=0x6f8130 "/home/ed/work/devicejs/tools/packageTools/tmp/.git/", 
    work_dir=0x6f80e0 "/home/ed/work/devicejs/tools/packageTools/tmp/", update_ignorecase=true) at ../vendor/libgit2/src/repository.c:968
#10 0x000000000041ed4d in repo_init_config (repo_dir=0x6f8130 "/home/ed/work/devicejs/tools/packageTools/tmp/.git/", work_dir=0x6f80e0 "/home/ed/work/devicejs/tools/packageTools/tmp/", flags=196624, mode=0)
    at ../vendor/libgit2/src/repository.c:1015
#11 0x000000000041fc4b in git_repository_init_ext (out=0x7fffffffded0, given_repo=0x4b9bf8 "tmp", opts=0x7fffffffde50) at ../vendor/libgit2/src/repository.c:1483
#12 0x000000000041fac2 in git_repository_init (repo_out=0x7fffffffded0, path=0x4b9bf8 "tmp", is_bare=0) at ../vendor/libgit2/src/repository.c:1446
#13 0x00000000004068da in git_clone (out=0x7fffffffdff8, url=0x4b9bd8 "git://github.com/WigWagCo/twlib", local_path=0x4b9bf8 "tmp", _options=0x7fffffffe090) at ../vendor/libgit2/src/clone.c:403
#14 0x0000000000405a53 in main ()
(gdb) q

1 个答案:

答案 0 :(得分:1)

人们对github的libgit2作出回应:

以下是libgit2 v0.21.1(已启用线程)的repo的工作克隆:

#include <git2.h>
#include <unistd.h>
#include <stdio.h>

int COMPLETE = 0;


typedef struct { 
int a;
/* … */ } progress_data;

int fetch_progress(
            const git_transfer_progress *stats,
            void *payload)
{
  progress_data *pd = (progress_data*)payload;

    int fetch_percent =
        (100 * stats->received_objects) /
        stats->total_objects;
    int index_percent =
        (100 * stats->indexed_objects) /
        stats->total_objects;
    int kbytes = stats->received_bytes / 1024;

    printf("network %3d%% (%4d kb, %5d/%5d)  /"
            "  index %3d%% (%5d/%5d)\n",
            fetch_percent, kbytes,
            stats->received_objects, stats->total_objects,
            index_percent,
            stats->indexed_objects, stats->total_objects);

    if(stats->indexed_objects >= stats->total_objects) {
        printf("COMPLETE=1\n");
        COMPLETE = 1;
    }

  /* Do something with network transfer progress */
    return 0; // return 0 for success. ~src/common.h:95 for info
}



void checkout_progress(
            const char *path,
            size_t cur,
            size_t tot,
            void *payload)
{
  progress_data *pd = (progress_data*)payload;

  printf("in checkout_progress\n");


  /* Do something with checkout progress */
}


int complete_cb(git_remote_completion_type type, void *data) {

    printf("complete\n");
}




int main(void) {

    git_threads_init();
    /* … */
    progress_data d = { 0 };
    git_clone_options clone_opts = GIT_CLONE_OPTIONS_INIT;
    git_checkout_options checkout_opts = GIT_CHECKOUT_OPTIONS_INIT;

    checkout_opts.checkout_strategy = GIT_CHECKOUT_FORCE;
    checkout_opts.progress_cb = checkout_progress;
    checkout_opts.progress_payload = &d;


    clone_opts.checkout_opts = checkout_opts;
    clone_opts.remote_callbacks.transfer_progress = fetch_progress;
    clone_opts.remote_callbacks.payload = &d;

    clone_opts.remote_callbacks.completion = complete_cb;

    git_repository *repo = NULL;

    const char *url = "git://github.com/WigWagCo/twlib";
    const char *path = "./tmp";


    printf("wait for completion.\n");


    int error = git_clone(&repo, url, path, &clone_opts);

    if(!COMPLETE)
        printf("Clone failed.\n");
    else
        printf("Clone complete.\n");

    printf("\n");
    if (error != 0) {
        const git_error *err = giterr_last();
        if (err) printf("ERROR %d: %s\n", err->klass, err->message);
        else printf("ERROR %d: no detailed info\n", error);
    } else
        if(repo) git_repository_free(repo);

    git_threads_shutdown();

}

/**
Build:
g++ -I./vendor/libgit2/include testhttps.cc ./build/Release/git2.a ./build/Release/zlib.a ./build/Release/http_parser.a -lpthread -lssl -lssh2 -lrt

 */